1 use auxil::ShaderStage;
2 use hal::{
3     adapter::MemoryProperties, buffer, device, format, image, memory, pass, pool, pso,
4     pso::VertexInputRate, query, queue::QueueFamilyId, window,
5 };
6 
7 use winapi::{
8     shared::{dxgi, dxgiformat, dxgitype, minwindef::TRUE, windef::HWND, winerror},
9     um::{d3d11, d3d11_1, d3d11sdklayers, d3dcommon},
10 };
11 
12 use wio::com::ComPtr;
13 
14 use std::{
15     fmt, mem,
16     ops::Range,
17     ptr,
18     sync::{Arc, Weak},
19 };
20 
21 use parking_lot::{Condvar, Mutex, RwLock};
22 
23 use crate::{
24     conv,
25     debug::{set_debug_name, set_debug_name_with_suffix, verify_debug_ascii},
26     internal, shader, Backend, Buffer, BufferView, CommandBuffer, CommandPool, ComputePipeline,
27     DescriptorContent, DescriptorIndex, DescriptorPool, DescriptorSet, DescriptorSetInfo,
28     DescriptorSetLayout, Fence, Framebuffer, GraphicsPipeline, Image, ImageView, InternalBuffer,
29     InternalImage, Memory, MultiStageData, PipelineLayout, QueryPool, RawFence,
30     RegisterAccumulator, RegisterData, RenderPass, ResourceIndex, Sampler, Semaphore, ShaderModule,
31     SubpassDesc, ViewInfo,
32 };
33 
34 //TODO: expose coherent type 0x2 when it's properly supported
35 const BUFFER_TYPE_MASK: u32 = 0x1 | 0x4;
36 
37 struct InputLayout {
38     raw: ComPtr<d3d11::ID3D11InputLayout>,
39     required_bindings: u32,
40     max_vertex_bindings: u32,
41     topology: d3d11::D3D11_PRIMITIVE_TOPOLOGY,
42     vertex_strides: Vec<u32>,
43 }
44 
45 #[derive(Clone)]
46 pub struct DepthStencilState {
47     pub raw: ComPtr<d3d11::ID3D11DepthStencilState>,
48     pub stencil_ref: pso::State<pso::StencilValue>,
49     pub read_only: bool,
50 }
51 
52 pub struct Device {
53     raw: ComPtr<d3d11::ID3D11Device>,
54     raw1: Option<ComPtr<d3d11_1::ID3D11Device1>>,
55     pub(crate) context: ComPtr<d3d11::ID3D11DeviceContext>,
56     features: hal::Features,
57     memory_properties: MemoryProperties,
58     pub(crate) internal: Arc<internal::Internal>,
59 }
60 
61 impl fmt::Debug for Device {
fmt(&self, fmt: &mut fmt::Formatter) -> fmt::Result62     fn fmt(&self, fmt: &mut fmt::Formatter) -> fmt::Result {
63         fmt.write_str("Device")
64     }
65 }
66 
67 impl Drop for Device {
drop(&mut self)68     fn drop(&mut self) {
69         if let Ok(debug) = self.raw.cast::<d3d11sdklayers::ID3D11Debug>() {
70             unsafe {
71                 debug.ReportLiveDeviceObjects(d3d11sdklayers::D3D11_RLDO_DETAIL);
72             }
73         }
74     }
75 }
76 
77 unsafe impl Send for Device {}
78 unsafe impl Sync for Device {}
79 
80 impl Device {
new( device: ComPtr<d3d11::ID3D11Device>, device1: Option<ComPtr<d3d11_1::ID3D11Device1>>, context: ComPtr<d3d11::ID3D11DeviceContext>, features: hal::Features, downlevel: hal::DownlevelProperties, memory_properties: MemoryProperties, feature_level: u32, ) -> Self81     pub fn new(
82         device: ComPtr<d3d11::ID3D11Device>,
83         device1: Option<ComPtr<d3d11_1::ID3D11Device1>>,
84         context: ComPtr<d3d11::ID3D11DeviceContext>,
85         features: hal::Features,
86         downlevel: hal::DownlevelProperties,
87         memory_properties: MemoryProperties,
88         feature_level: u32,
89     ) -> Self {
90         Device {
91             internal: Arc::new(internal::Internal::new(
92                 &device,
93                 features,
94                 feature_level,
95                 downlevel,
96             )),
97             raw: device,
98             raw1: device1,
99             context,
100             features,
101             memory_properties,
102         }
103     }
104 
as_raw(&self) -> *mut d3d11::ID3D11Device105     pub fn as_raw(&self) -> *mut d3d11::ID3D11Device {
106         self.raw.as_raw()
107     }
108 
create_rasterizer_state( &self, rasterizer_desc: &pso::Rasterizer, multisampling_desc: &Option<pso::Multisampling>, ) -> Result<ComPtr<d3d11::ID3D11RasterizerState>, pso::CreationError>109     fn create_rasterizer_state(
110         &self,
111         rasterizer_desc: &pso::Rasterizer,
112         multisampling_desc: &Option<pso::Multisampling>,
113     ) -> Result<ComPtr<d3d11::ID3D11RasterizerState>, pso::CreationError> {
114         let mut rasterizer = ptr::null_mut();
115         let desc = conv::map_rasterizer_desc(rasterizer_desc, multisampling_desc);
116 
117         let hr = unsafe {
118             self.raw
119                 .CreateRasterizerState(&desc, &mut rasterizer as *mut *mut _ as *mut *mut _)
120         };
121 
122         if winerror::SUCCEEDED(hr) {
123             Ok(unsafe { ComPtr::from_raw(rasterizer) })
124         } else {
125             Err(pso::CreationError::Other)
126         }
127     }
128 
create_blend_state( &self, blend_desc: &pso::BlendDesc, multisampling: &Option<pso::Multisampling>, ) -> Result<ComPtr<d3d11::ID3D11BlendState>, pso::CreationError>129     fn create_blend_state(
130         &self,
131         blend_desc: &pso::BlendDesc,
132         multisampling: &Option<pso::Multisampling>,
133     ) -> Result<ComPtr<d3d11::ID3D11BlendState>, pso::CreationError> {
134         let mut blend = ptr::null_mut();
135         let desc = conv::map_blend_desc(blend_desc, multisampling);
136 
137         let hr = unsafe {
138             self.raw
139                 .CreateBlendState(&desc, &mut blend as *mut *mut _ as *mut *mut _)
140         };
141 
142         if winerror::SUCCEEDED(hr) {
143             Ok(unsafe { ComPtr::from_raw(blend) })
144         } else {
145             Err(pso::CreationError::Other)
146         }
147     }
148 
create_depth_stencil_state( &self, depth_desc: &pso::DepthStencilDesc, ) -> Result<DepthStencilState, pso::CreationError>149     fn create_depth_stencil_state(
150         &self,
151         depth_desc: &pso::DepthStencilDesc,
152     ) -> Result<DepthStencilState, pso::CreationError> {
153         let mut depth = ptr::null_mut();
154         let (desc, stencil_ref, read_only) = conv::map_depth_stencil_desc(depth_desc);
155 
156         let hr = unsafe {
157             self.raw
158                 .CreateDepthStencilState(&desc, &mut depth as *mut *mut _ as *mut *mut _)
159         };
160 
161         if winerror::SUCCEEDED(hr) {
162             Ok(DepthStencilState {
163                 raw: unsafe { ComPtr::from_raw(depth) },
164                 stencil_ref,
165                 read_only,
166             })
167         } else {
168             Err(pso::CreationError::Other)
169         }
170     }
171 
create_input_layout( &self, vs: ComPtr<d3dcommon::ID3DBlob>, vertex_buffers: &[pso::VertexBufferDesc], attributes: &[pso::AttributeDesc], input_assembler: &pso::InputAssemblerDesc, vertex_semantic_remapping: auxil::FastHashMap<u32, Option<(u32, u32)>>, ) -> Result<InputLayout, pso::CreationError>172     fn create_input_layout(
173         &self,
174         vs: ComPtr<d3dcommon::ID3DBlob>,
175         vertex_buffers: &[pso::VertexBufferDesc],
176         attributes: &[pso::AttributeDesc],
177         input_assembler: &pso::InputAssemblerDesc,
178         vertex_semantic_remapping: auxil::FastHashMap<u32, Option<(u32, u32)>>,
179     ) -> Result<InputLayout, pso::CreationError> {
180         let mut layout = ptr::null_mut();
181 
182         let mut vertex_strides = Vec::new();
183         let mut required_bindings = 0u32;
184         let mut max_vertex_bindings = 0u32;
185         for buffer in vertex_buffers {
186             required_bindings |= 1 << buffer.binding as u32;
187             max_vertex_bindings = max_vertex_bindings.max(1u32 + buffer.binding as u32);
188 
189             while vertex_strides.len() <= buffer.binding as usize {
190                 vertex_strides.push(0);
191             }
192 
193             vertex_strides[buffer.binding as usize] = buffer.stride;
194         }
195 
196         // See [`shader::introspect_spirv_vertex_semantic_remapping`] for details of why this is needed.
197         let semantics: Vec<_> = attributes
198             .iter()
199             .map(
200                 |attrib| match vertex_semantic_remapping.get(&attrib.location) {
201                     Some(Some((major, minor))) => {
202                         let name = std::borrow::Cow::Owned(format!("TEXCOORD{}_\0", major));
203                         let location = *minor;
204                         (name, location)
205                     }
206                     _ => {
207                         let name = std::borrow::Cow::Borrowed("TEXCOORD\0");
208                         let location = attrib.location;
209                         (name, location)
210                     }
211                 },
212             )
213             .collect();
214 
215         let input_elements = attributes
216             .iter()
217             .zip(semantics.iter())
218             .filter_map(|(attrib, (semantic_name, semantic_index))| {
219                 let buffer_desc = match vertex_buffers
220                     .iter()
221                     .find(|buffer_desc| buffer_desc.binding == attrib.binding)
222                 {
223                     Some(buffer_desc) => buffer_desc,
224                     None => {
225                         // TODO:
226                         // error!("Couldn't find associated vertex buffer description {:?}", attrib.binding);
227                         return Some(Err(pso::CreationError::Other));
228                     }
229                 };
230 
231                 let (slot_class, step_rate) = match buffer_desc.rate {
232                     VertexInputRate::Vertex => (d3d11::D3D11_INPUT_PER_VERTEX_DATA, 0),
233                     VertexInputRate::Instance(divisor) => {
234                         (d3d11::D3D11_INPUT_PER_INSTANCE_DATA, divisor)
235                     }
236                 };
237                 let format = attrib.element.format;
238 
239                 Some(Ok(d3d11::D3D11_INPUT_ELEMENT_DESC {
240                     SemanticName: semantic_name.as_ptr() as *const _, // Semantic name used by SPIRV-Cross
241                     SemanticIndex: *semantic_index,
242                     Format: match conv::map_format(format) {
243                         Some(fm) => fm,
244                         None => {
245                             // TODO:
246                             // error!("Unable to find DXGI format for {:?}", format);
247                             return Some(Err(pso::CreationError::Other));
248                         }
249                     },
250                     InputSlot: attrib.binding as _,
251                     AlignedByteOffset: attrib.element.offset,
252                     InputSlotClass: slot_class,
253                     InstanceDataStepRate: step_rate as _,
254                 }))
255             })
256             .collect::<Result<Vec<_>, _>>()?;
257 
258         let hr = unsafe {
259             self.raw.CreateInputLayout(
260                 input_elements.as_ptr(),
261                 input_elements.len() as _,
262                 vs.GetBufferPointer(),
263                 vs.GetBufferSize(),
264                 &mut layout as *mut *mut _ as *mut *mut _,
265             )
266         };
267 
268         if winerror::SUCCEEDED(hr) {
269             let topology = conv::map_topology(input_assembler);
270 
271             Ok(InputLayout {
272                 raw: unsafe { ComPtr::from_raw(layout) },
273                 required_bindings,
274                 max_vertex_bindings,
275                 topology,
276                 vertex_strides,
277             })
278         } else {
279             error!("CreateInputLayout error 0x{:X}", hr);
280             Err(pso::CreationError::Other)
281         }
282     }
283 
create_vertex_shader( &self, blob: ComPtr<d3dcommon::ID3DBlob>, ) -> Result<ComPtr<d3d11::ID3D11VertexShader>, pso::CreationError>284     fn create_vertex_shader(
285         &self,
286         blob: ComPtr<d3dcommon::ID3DBlob>,
287     ) -> Result<ComPtr<d3d11::ID3D11VertexShader>, pso::CreationError> {
288         let mut vs = ptr::null_mut();
289 
290         let hr = unsafe {
291             self.raw.CreateVertexShader(
292                 blob.GetBufferPointer(),
293                 blob.GetBufferSize(),
294                 ptr::null_mut(),
295                 &mut vs as *mut *mut _ as *mut *mut _,
296             )
297         };
298 
299         if winerror::SUCCEEDED(hr) {
300             Ok(unsafe { ComPtr::from_raw(vs) })
301         } else {
302             Err(pso::CreationError::ShaderCreationError(
303                 pso::ShaderStageFlags::VERTEX,
304                 String::from("Failed to create a vertex shader"),
305             ))
306         }
307     }
308 
create_pixel_shader( &self, blob: ComPtr<d3dcommon::ID3DBlob>, ) -> Result<ComPtr<d3d11::ID3D11PixelShader>, pso::CreationError>309     fn create_pixel_shader(
310         &self,
311         blob: ComPtr<d3dcommon::ID3DBlob>,
312     ) -> Result<ComPtr<d3d11::ID3D11PixelShader>, pso::CreationError> {
313         let mut ps = ptr::null_mut();
314 
315         let hr = unsafe {
316             self.raw.CreatePixelShader(
317                 blob.GetBufferPointer(),
318                 blob.GetBufferSize(),
319                 ptr::null_mut(),
320                 &mut ps as *mut *mut _ as *mut *mut _,
321             )
322         };
323 
324         if winerror::SUCCEEDED(hr) {
325             Ok(unsafe { ComPtr::from_raw(ps) })
326         } else {
327             Err(pso::CreationError::ShaderCreationError(
328                 pso::ShaderStageFlags::FRAGMENT,
329                 String::from("Failed to create a pixel shader"),
330             ))
331         }
332     }
333 
create_geometry_shader( &self, blob: ComPtr<d3dcommon::ID3DBlob>, ) -> Result<ComPtr<d3d11::ID3D11GeometryShader>, pso::CreationError>334     fn create_geometry_shader(
335         &self,
336         blob: ComPtr<d3dcommon::ID3DBlob>,
337     ) -> Result<ComPtr<d3d11::ID3D11GeometryShader>, pso::CreationError> {
338         let mut gs = ptr::null_mut();
339 
340         let hr = unsafe {
341             self.raw.CreateGeometryShader(
342                 blob.GetBufferPointer(),
343                 blob.GetBufferSize(),
344                 ptr::null_mut(),
345                 &mut gs as *mut *mut _ as *mut *mut _,
346             )
347         };
348 
349         if winerror::SUCCEEDED(hr) {
350             Ok(unsafe { ComPtr::from_raw(gs) })
351         } else {
352             Err(pso::CreationError::ShaderCreationError(
353                 pso::ShaderStageFlags::GEOMETRY,
354                 String::from("Failed to create a geometry shader"),
355             ))
356         }
357     }
358 
create_hull_shader( &self, blob: ComPtr<d3dcommon::ID3DBlob>, ) -> Result<ComPtr<d3d11::ID3D11HullShader>, pso::CreationError>359     fn create_hull_shader(
360         &self,
361         blob: ComPtr<d3dcommon::ID3DBlob>,
362     ) -> Result<ComPtr<d3d11::ID3D11HullShader>, pso::CreationError> {
363         let mut hs = ptr::null_mut();
364 
365         let hr = unsafe {
366             self.raw.CreateHullShader(
367                 blob.GetBufferPointer(),
368                 blob.GetBufferSize(),
369                 ptr::null_mut(),
370                 &mut hs as *mut *mut _ as *mut *mut _,
371             )
372         };
373 
374         if winerror::SUCCEEDED(hr) {
375             Ok(unsafe { ComPtr::from_raw(hs) })
376         } else {
377             Err(pso::CreationError::ShaderCreationError(
378                 pso::ShaderStageFlags::HULL,
379                 String::from("Failed to create a hull shader"),
380             ))
381         }
382     }
383 
create_domain_shader( &self, blob: ComPtr<d3dcommon::ID3DBlob>, ) -> Result<ComPtr<d3d11::ID3D11DomainShader>, pso::CreationError>384     fn create_domain_shader(
385         &self,
386         blob: ComPtr<d3dcommon::ID3DBlob>,
387     ) -> Result<ComPtr<d3d11::ID3D11DomainShader>, pso::CreationError> {
388         let mut ds = ptr::null_mut();
389 
390         let hr = unsafe {
391             self.raw.CreateDomainShader(
392                 blob.GetBufferPointer(),
393                 blob.GetBufferSize(),
394                 ptr::null_mut(),
395                 &mut ds as *mut *mut _ as *mut *mut _,
396             )
397         };
398 
399         if winerror::SUCCEEDED(hr) {
400             Ok(unsafe { ComPtr::from_raw(ds) })
401         } else {
402             Err(pso::CreationError::ShaderCreationError(
403                 pso::ShaderStageFlags::DOMAIN,
404                 String::from("Failed to create a domain shader"),
405             ))
406         }
407     }
408 
create_compute_shader( &self, blob: ComPtr<d3dcommon::ID3DBlob>, ) -> Result<ComPtr<d3d11::ID3D11ComputeShader>, pso::CreationError>409     fn create_compute_shader(
410         &self,
411         blob: ComPtr<d3dcommon::ID3DBlob>,
412     ) -> Result<ComPtr<d3d11::ID3D11ComputeShader>, pso::CreationError> {
413         let mut cs = ptr::null_mut();
414 
415         let hr = unsafe {
416             self.raw.CreateComputeShader(
417                 blob.GetBufferPointer(),
418                 blob.GetBufferSize(),
419                 ptr::null_mut(),
420                 &mut cs as *mut *mut _ as *mut *mut _,
421             )
422         };
423 
424         if winerror::SUCCEEDED(hr) {
425             Ok(unsafe { ComPtr::from_raw(cs) })
426         } else {
427             Err(pso::CreationError::ShaderCreationError(
428                 pso::ShaderStageFlags::COMPUTE,
429                 String::from("Failed to create a compute shader"),
430             ))
431         }
432     }
433 
434     // TODO: fix return type..
extract_entry_point( stage: ShaderStage, source: &pso::EntryPoint<Backend>, layout: &PipelineLayout, features: &hal::Features, device_feature_level: u32, ) -> Result<Option<ComPtr<d3dcommon::ID3DBlob>>, pso::CreationError>435     fn extract_entry_point(
436         stage: ShaderStage,
437         source: &pso::EntryPoint<Backend>,
438         layout: &PipelineLayout,
439         features: &hal::Features,
440         device_feature_level: u32,
441     ) -> Result<Option<ComPtr<d3dcommon::ID3DBlob>>, pso::CreationError> {
442         // TODO: entrypoint stuff
443         match *source.module {
444             ShaderModule::Dxbc(ref _shader) => Err(pso::CreationError::ShaderCreationError(
445                 pso::ShaderStageFlags::ALL,
446                 String::from("DXBC modules are not supported yet"),
447             )),
448             ShaderModule::Spirv(ref raw_data) => Ok(shader::compile_spirv_entrypoint(
449                 raw_data,
450                 stage,
451                 source,
452                 layout,
453                 features,
454                 device_feature_level,
455             )?),
456         }
457     }
458 
view_image_as_shader_resource( &self, info: &ViewInfo, ) -> Result<ComPtr<d3d11::ID3D11ShaderResourceView>, image::ViewCreationError>459     fn view_image_as_shader_resource(
460         &self,
461         info: &ViewInfo,
462     ) -> Result<ComPtr<d3d11::ID3D11ShaderResourceView>, image::ViewCreationError> {
463         let mut desc: d3d11::D3D11_SHADER_RESOURCE_VIEW_DESC = unsafe { mem::zeroed() };
464         desc.Format = info.format;
465         if desc.Format == dxgiformat::DXGI_FORMAT_D32_FLOAT_S8X24_UINT {
466             desc.Format = dxgiformat::DXGI_FORMAT_R32_FLOAT_X8X24_TYPELESS;
467         }
468 
469         #[allow(non_snake_case)]
470         let MostDetailedMip = info.levels.start as _;
471         #[allow(non_snake_case)]
472         let MipLevels = (info.levels.end - info.levels.start) as _;
473         #[allow(non_snake_case)]
474         let FirstArraySlice = info.layers.start as _;
475         #[allow(non_snake_case)]
476         let ArraySize = (info.layers.end - info.layers.start) as _;
477 
478         match info.view_kind {
479             image::ViewKind::D1 => {
480                 desc.ViewDimension = d3dcommon::D3D11_SRV_DIMENSION_TEXTURE1D;
481                 *unsafe { desc.u.Texture1D_mut() } = d3d11::D3D11_TEX1D_SRV {
482                     MostDetailedMip,
483                     MipLevels,
484                 }
485             }
486             image::ViewKind::D1Array => {
487                 desc.ViewDimension = d3dcommon::D3D11_SRV_DIMENSION_TEXTURE1DARRAY;
488                 *unsafe { desc.u.Texture1DArray_mut() } = d3d11::D3D11_TEX1D_ARRAY_SRV {
489                     MostDetailedMip,
490                     MipLevels,
491                     FirstArraySlice,
492                     ArraySize,
493                 }
494             }
495             image::ViewKind::D2 if info.kind.num_samples() > 1 => {
496                 desc.ViewDimension = d3dcommon::D3D11_SRV_DIMENSION_TEXTURE2DMS;
497                 *unsafe { desc.u.Texture2DMS_mut() } = d3d11::D3D11_TEX2DMS_SRV {
498                     UnusedField_NothingToDefine: 0,
499                 }
500             }
501             image::ViewKind::D2 => {
502                 desc.ViewDimension = d3dcommon::D3D11_SRV_DIMENSION_TEXTURE2D;
503                 *unsafe { desc.u.Texture2D_mut() } = d3d11::D3D11_TEX2D_SRV {
504                     MostDetailedMip,
505                     MipLevels,
506                 }
507             }
508             image::ViewKind::D2Array if info.kind.num_samples() > 1 => {
509                 desc.ViewDimension = d3dcommon::D3D11_SRV_DIMENSION_TEXTURE2DMSARRAY;
510                 *unsafe { desc.u.Texture2DMSArray_mut() } = d3d11::D3D11_TEX2DMS_ARRAY_SRV {
511                     FirstArraySlice,
512                     ArraySize,
513                 }
514             }
515             image::ViewKind::D2Array => {
516                 desc.ViewDimension = d3dcommon::D3D11_SRV_DIMENSION_TEXTURE2DARRAY;
517                 *unsafe { desc.u.Texture2DArray_mut() } = d3d11::D3D11_TEX2D_ARRAY_SRV {
518                     MostDetailedMip,
519                     MipLevels,
520                     FirstArraySlice,
521                     ArraySize,
522                 }
523             }
524             image::ViewKind::D3 => {
525                 desc.ViewDimension = d3dcommon::D3D11_SRV_DIMENSION_TEXTURE3D;
526                 *unsafe { desc.u.Texture3D_mut() } = d3d11::D3D11_TEX3D_SRV {
527                     MostDetailedMip,
528                     MipLevels,
529                 }
530             }
531             image::ViewKind::Cube => {
532                 desc.ViewDimension = d3dcommon::D3D11_SRV_DIMENSION_TEXTURECUBE;
533                 *unsafe { desc.u.TextureCube_mut() } = d3d11::D3D11_TEXCUBE_SRV {
534                     MostDetailedMip,
535                     MipLevels,
536                 }
537             }
538             image::ViewKind::CubeArray => {
539                 desc.ViewDimension = d3dcommon::D3D11_SRV_DIMENSION_TEXTURECUBEARRAY;
540                 *unsafe { desc.u.TextureCubeArray_mut() } = d3d11::D3D11_TEXCUBE_ARRAY_SRV {
541                     MostDetailedMip,
542                     MipLevels,
543                     First2DArrayFace: FirstArraySlice,
544                     NumCubes: ArraySize / 6,
545                 }
546             }
547         }
548 
549         let mut srv = ptr::null_mut();
550         let hr = unsafe {
551             self.raw.CreateShaderResourceView(
552                 info.resource,
553                 &desc,
554                 &mut srv as *mut *mut _ as *mut *mut _,
555             )
556         };
557 
558         if winerror::SUCCEEDED(hr) {
559             Ok(unsafe { ComPtr::from_raw(srv) })
560         } else {
561             Err(image::ViewCreationError::Unsupported)
562         }
563     }
564 
view_image_as_unordered_access( &self, info: &ViewInfo, ) -> Result<ComPtr<d3d11::ID3D11UnorderedAccessView>, image::ViewCreationError>565     fn view_image_as_unordered_access(
566         &self,
567         info: &ViewInfo,
568     ) -> Result<ComPtr<d3d11::ID3D11UnorderedAccessView>, image::ViewCreationError> {
569         let mut desc: d3d11::D3D11_UNORDERED_ACCESS_VIEW_DESC = unsafe { mem::zeroed() };
570         desc.Format = info.format;
571 
572         #[allow(non_snake_case)]
573         let MipSlice = info.levels.start as _;
574         #[allow(non_snake_case)]
575         let FirstArraySlice = info.layers.start as _;
576         #[allow(non_snake_case)]
577         let ArraySize = (info.layers.end - info.layers.start) as _;
578 
579         match info.view_kind {
580             image::ViewKind::D1 => {
581                 desc.ViewDimension = d3d11::D3D11_UAV_DIMENSION_TEXTURE1D;
582                 *unsafe { desc.u.Texture1D_mut() } = d3d11::D3D11_TEX1D_UAV {
583                     MipSlice: info.levels.start as _,
584                 }
585             }
586             image::ViewKind::D1Array => {
587                 desc.ViewDimension = d3d11::D3D11_UAV_DIMENSION_TEXTURE1DARRAY;
588                 *unsafe { desc.u.Texture1DArray_mut() } = d3d11::D3D11_TEX1D_ARRAY_UAV {
589                     MipSlice,
590                     FirstArraySlice,
591                     ArraySize,
592                 }
593             }
594             image::ViewKind::D2 => {
595                 desc.ViewDimension = d3d11::D3D11_UAV_DIMENSION_TEXTURE2D;
596                 *unsafe { desc.u.Texture2D_mut() } = d3d11::D3D11_TEX2D_UAV {
597                     MipSlice: info.levels.start as _,
598                 }
599             }
600             image::ViewKind::D2Array => {
601                 desc.ViewDimension = d3d11::D3D11_UAV_DIMENSION_TEXTURE2DARRAY;
602                 *unsafe { desc.u.Texture2DArray_mut() } = d3d11::D3D11_TEX2D_ARRAY_UAV {
603                     MipSlice,
604                     FirstArraySlice,
605                     ArraySize,
606                 }
607             }
608             image::ViewKind::D3 => {
609                 desc.ViewDimension = d3d11::D3D11_UAV_DIMENSION_TEXTURE3D;
610                 *unsafe { desc.u.Texture3D_mut() } = d3d11::D3D11_TEX3D_UAV {
611                     MipSlice,
612                     FirstWSlice: FirstArraySlice,
613                     WSize: ArraySize,
614                 }
615             }
616             _ => unimplemented!(),
617         }
618 
619         let mut uav = ptr::null_mut();
620         let hr = unsafe {
621             self.raw.CreateUnorderedAccessView(
622                 info.resource,
623                 &desc,
624                 &mut uav as *mut *mut _ as *mut *mut _,
625             )
626         };
627 
628         if winerror::SUCCEEDED(hr) {
629             Ok(unsafe { ComPtr::from_raw(uav) })
630         } else {
631             error!("CreateUnorderedAccessView failed: 0x{:x}", hr);
632 
633             Err(image::ViewCreationError::Unsupported)
634         }
635     }
636 
view_image_as_render_target( &self, info: &ViewInfo, ) -> Result<ComPtr<d3d11::ID3D11RenderTargetView>, image::ViewCreationError>637     pub(crate) fn view_image_as_render_target(
638         &self,
639         info: &ViewInfo,
640     ) -> Result<ComPtr<d3d11::ID3D11RenderTargetView>, image::ViewCreationError> {
641         let mut desc: d3d11::D3D11_RENDER_TARGET_VIEW_DESC = unsafe { mem::zeroed() };
642         desc.Format = info.format;
643 
644         #[allow(non_snake_case)]
645         let MipSlice = info.levels.start as _;
646         #[allow(non_snake_case)]
647         let FirstArraySlice = info.layers.start as _;
648         #[allow(non_snake_case)]
649         let ArraySize = (info.layers.end - info.layers.start) as _;
650 
651         match info.view_kind {
652             image::ViewKind::D1 => {
653                 desc.ViewDimension = d3d11::D3D11_RTV_DIMENSION_TEXTURE1D;
654                 *unsafe { desc.u.Texture1D_mut() } = d3d11::D3D11_TEX1D_RTV { MipSlice }
655             }
656             image::ViewKind::D1Array => {
657                 desc.ViewDimension = d3d11::D3D11_RTV_DIMENSION_TEXTURE1DARRAY;
658                 *unsafe { desc.u.Texture1DArray_mut() } = d3d11::D3D11_TEX1D_ARRAY_RTV {
659                     MipSlice,
660                     FirstArraySlice,
661                     ArraySize,
662                 }
663             }
664             image::ViewKind::D2 => {
665                 if info.kind.num_samples() > 1 {
666                     desc.ViewDimension = d3d11::D3D11_RTV_DIMENSION_TEXTURE2DMS;
667                     *unsafe { desc.u.Texture2DMS_mut() } = d3d11::D3D11_TEX2DMS_RTV {
668                         UnusedField_NothingToDefine: 0,
669                     }
670                 } else {
671                     desc.ViewDimension = d3d11::D3D11_RTV_DIMENSION_TEXTURE2D;
672                     *unsafe { desc.u.Texture2D_mut() } = d3d11::D3D11_TEX2D_RTV { MipSlice }
673                 }
674             }
675             image::ViewKind::D2Array => {
676                 if info.kind.num_samples() > 1 {
677                     desc.ViewDimension = d3d11::D3D11_RTV_DIMENSION_TEXTURE2DMSARRAY;
678                     *unsafe { desc.u.Texture2DMSArray_mut() } = d3d11::D3D11_TEX2DMS_ARRAY_RTV {
679                         FirstArraySlice,
680                         ArraySize,
681                     }
682                 } else {
683                     desc.ViewDimension = d3d11::D3D11_RTV_DIMENSION_TEXTURE2DARRAY;
684                     *unsafe { desc.u.Texture2DArray_mut() } = d3d11::D3D11_TEX2D_ARRAY_RTV {
685                         MipSlice,
686                         FirstArraySlice,
687                         ArraySize,
688                     }
689                 }
690             }
691             image::ViewKind::D3 => {
692                 desc.ViewDimension = d3d11::D3D11_RTV_DIMENSION_TEXTURE3D;
693                 *unsafe { desc.u.Texture3D_mut() } = d3d11::D3D11_TEX3D_RTV {
694                     MipSlice,
695                     FirstWSlice: FirstArraySlice,
696                     WSize: ArraySize,
697                 }
698             }
699             _ => unimplemented!(),
700         }
701 
702         let mut rtv = ptr::null_mut();
703         let hr = unsafe {
704             self.raw.CreateRenderTargetView(
705                 info.resource,
706                 &desc,
707                 &mut rtv as *mut *mut _ as *mut *mut _,
708             )
709         };
710 
711         if winerror::SUCCEEDED(hr) {
712             Ok(unsafe { ComPtr::from_raw(rtv) })
713         } else {
714             error!("CreateRenderTargetView failed: 0x{:x}", hr);
715 
716             Err(image::ViewCreationError::Unsupported)
717         }
718     }
719 
view_image_as_depth_stencil( &self, info: &ViewInfo, read_only_stencil: Option<bool>, ) -> Result<ComPtr<d3d11::ID3D11DepthStencilView>, image::ViewCreationError>720     fn view_image_as_depth_stencil(
721         &self,
722         info: &ViewInfo,
723         read_only_stencil: Option<bool>,
724     ) -> Result<ComPtr<d3d11::ID3D11DepthStencilView>, image::ViewCreationError> {
725         #![allow(non_snake_case)]
726 
727         let MipSlice = info.levels.start as _;
728         let FirstArraySlice = info.layers.start as _;
729         let ArraySize = (info.layers.end - info.layers.start) as _;
730         assert_eq!(info.levels.start + 1, info.levels.end);
731         assert!(info.layers.end <= info.kind.num_layers());
732 
733         let mut desc: d3d11::D3D11_DEPTH_STENCIL_VIEW_DESC = unsafe { mem::zeroed() };
734         desc.Format = info.format;
735 
736         if let Some(stencil) = read_only_stencil {
737             desc.Flags = match stencil {
738                 true => d3d11::D3D11_DSV_READ_ONLY_DEPTH | d3d11::D3D11_DSV_READ_ONLY_STENCIL,
739                 false => d3d11::D3D11_DSV_READ_ONLY_DEPTH,
740             }
741         }
742 
743         match info.view_kind {
744             image::ViewKind::D2 => {
745                 if info.kind.num_samples() > 1 {
746                     desc.ViewDimension = d3d11::D3D11_DSV_DIMENSION_TEXTURE2DMS;
747                     *unsafe { desc.u.Texture2DMS_mut() } = d3d11::D3D11_TEX2DMS_DSV {
748                         UnusedField_NothingToDefine: 0,
749                     }
750                 } else {
751                     desc.ViewDimension = d3d11::D3D11_DSV_DIMENSION_TEXTURE2D;
752                     *unsafe { desc.u.Texture2D_mut() } = d3d11::D3D11_TEX2D_DSV { MipSlice }
753                 }
754             }
755             image::ViewKind::D2Array => {
756                 if info.kind.num_samples() > 1 {
757                     desc.ViewDimension = d3d11::D3D11_DSV_DIMENSION_TEXTURE2DMSARRAY;
758                     *unsafe { desc.u.Texture2DMSArray_mut() } = d3d11::D3D11_TEX2DMS_ARRAY_DSV {
759                         FirstArraySlice,
760                         ArraySize,
761                     }
762                 } else {
763                     desc.ViewDimension = d3d11::D3D11_DSV_DIMENSION_TEXTURE2DARRAY;
764                     *unsafe { desc.u.Texture2DArray_mut() } = d3d11::D3D11_TEX2D_ARRAY_DSV {
765                         MipSlice,
766                         FirstArraySlice,
767                         ArraySize,
768                     }
769                 }
770             }
771             image::ViewKind::D1
772             | image::ViewKind::D1Array
773             | image::ViewKind::D3
774             | image::ViewKind::Cube
775             | image::ViewKind::CubeArray => {
776                 warn!(
777                     "3D and cube views are not supported for the image, kind: {:?}",
778                     info.kind
779                 );
780                 return Err(image::ViewCreationError::BadKind(info.view_kind));
781             }
782         }
783 
784         let mut dsv = ptr::null_mut();
785         let hr = unsafe {
786             self.raw.CreateDepthStencilView(
787                 info.resource,
788                 &desc,
789                 &mut dsv as *mut *mut _ as *mut *mut _,
790             )
791         };
792 
793         if winerror::SUCCEEDED(hr) {
794             Ok(unsafe { ComPtr::from_raw(dsv) })
795         } else {
796             error!("CreateDepthStencilView failed: 0x{:x}", hr);
797 
798             Err(image::ViewCreationError::Unsupported)
799         }
800     }
801 
create_swapchain_impl( &self, config: &window::SwapchainConfig, window_handle: HWND, factory: ComPtr<dxgi::IDXGIFactory>, ) -> Result<(ComPtr<dxgi::IDXGISwapChain>, dxgiformat::DXGI_FORMAT), window::SwapchainError>802     pub(crate) fn create_swapchain_impl(
803         &self,
804         config: &window::SwapchainConfig,
805         window_handle: HWND,
806         factory: ComPtr<dxgi::IDXGIFactory>,
807     ) -> Result<(ComPtr<dxgi::IDXGISwapChain>, dxgiformat::DXGI_FORMAT), window::SwapchainError>
808     {
809         // TODO: use IDXGIFactory2 for >=11.1
810         // TODO: this function should be able to fail (Result)?
811 
812         debug!("{:#?}", config);
813         let non_srgb_format = conv::map_format_nosrgb(config.format).unwrap();
814 
815         let mut desc = dxgi::DXGI_SWAP_CHAIN_DESC {
816             BufferDesc: dxgitype::DXGI_MODE_DESC {
817                 Width: config.extent.width,
818                 Height: config.extent.height,
819                 // TODO: should this grab max value of all monitor hz? vsync
820                 //       will clamp to current monitor anyways?
821                 RefreshRate: dxgitype::DXGI_RATIONAL {
822                     Numerator: 1,
823                     Denominator: 60,
824                 },
825                 Format: non_srgb_format,
826                 ScanlineOrdering: dxgitype::DXGI_MODE_SCANLINE_ORDER_UNSPECIFIED,
827                 Scaling: dxgitype::DXGI_MODE_SCALING_UNSPECIFIED,
828             },
829             SampleDesc: dxgitype::DXGI_SAMPLE_DESC {
830                 Count: 1,
831                 Quality: 0,
832             },
833             BufferUsage: dxgitype::DXGI_USAGE_RENDER_TARGET_OUTPUT,
834             BufferCount: config.image_count,
835             OutputWindow: window_handle,
836             // TODO:
837             Windowed: TRUE,
838             // TODO:
839             SwapEffect: dxgi::DXGI_SWAP_EFFECT_DISCARD,
840             Flags: 0,
841         };
842 
843         let dxgi_swapchain = {
844             let mut swapchain: *mut dxgi::IDXGISwapChain = ptr::null_mut();
845             let hr = unsafe {
846                 factory.CreateSwapChain(
847                     self.raw.as_raw() as *mut _,
848                     &mut desc as *mut _,
849                     &mut swapchain as *mut *mut _ as *mut *mut _,
850                 )
851             };
852             assert_eq!(hr, winerror::S_OK);
853 
854             unsafe { ComPtr::from_raw(swapchain) }
855         };
856         Ok((dxgi_swapchain, non_srgb_format))
857     }
858 }
859 
860 impl device::Device<Backend> for Device {
allocate_memory( &self, mem_type: hal::MemoryTypeId, size: u64, ) -> Result<Memory, device::AllocationError>861     unsafe fn allocate_memory(
862         &self,
863         mem_type: hal::MemoryTypeId,
864         size: u64,
865     ) -> Result<Memory, device::AllocationError> {
866         let properties = self.memory_properties.memory_types[mem_type.0].properties;
867         let host_ptr = if properties.contains(hal::memory::Properties::CPU_VISIBLE) {
868             let mut data = vec![0u8; size as usize];
869             let ptr = data.as_mut_ptr();
870             mem::forget(data);
871             ptr
872         } else {
873             ptr::null_mut()
874         };
875         Ok(Memory {
876             properties,
877             size,
878             host_ptr,
879             local_buffers: Arc::new(RwLock::new(thunderdome::Arena::new())),
880         })
881     }
882 
create_command_pool( &self, _family: QueueFamilyId, _create_flags: pool::CommandPoolCreateFlags, ) -> Result<CommandPool, device::OutOfMemory>883     unsafe fn create_command_pool(
884         &self,
885         _family: QueueFamilyId,
886         _create_flags: pool::CommandPoolCreateFlags,
887     ) -> Result<CommandPool, device::OutOfMemory> {
888         // TODO:
889         Ok(CommandPool {
890             device: self.raw.clone(),
891             device1: self.raw1.clone(),
892             internal: Arc::clone(&self.internal),
893         })
894     }
895 
destroy_command_pool(&self, _pool: CommandPool)896     unsafe fn destroy_command_pool(&self, _pool: CommandPool) {
897         // automatic
898     }
899 
create_render_pass<'a, Ia, Is, Id>( &self, attachments: Ia, subpasses: Is, _dependencies: Id, ) -> Result<RenderPass, device::OutOfMemory> where Ia: Iterator<Item = pass::Attachment>, Is: Iterator<Item = pass::SubpassDesc<'a>>,900     unsafe fn create_render_pass<'a, Ia, Is, Id>(
901         &self,
902         attachments: Ia,
903         subpasses: Is,
904         _dependencies: Id,
905     ) -> Result<RenderPass, device::OutOfMemory>
906     where
907         Ia: Iterator<Item = pass::Attachment>,
908         Is: Iterator<Item = pass::SubpassDesc<'a>>,
909     {
910         Ok(RenderPass {
911             attachments: attachments.collect(),
912             subpasses: subpasses
913                 .map(|desc| SubpassDesc {
914                     color_attachments: desc.colors.to_vec(),
915                     depth_stencil_attachment: desc.depth_stencil.cloned(),
916                     input_attachments: desc.inputs.to_vec(),
917                     resolve_attachments: desc.resolves.to_vec(),
918                 })
919                 .collect(),
920         })
921     }
922 
create_pipeline_layout<'a, Is, Ic>( &self, set_layouts: Is, _push_constant_ranges: Ic, ) -> Result<PipelineLayout, device::OutOfMemory> where Is: Iterator<Item = &'a DescriptorSetLayout>, Ic: Iterator<Item = (pso::ShaderStageFlags, Range<u32>)>,923     unsafe fn create_pipeline_layout<'a, Is, Ic>(
924         &self,
925         set_layouts: Is,
926         _push_constant_ranges: Ic,
927     ) -> Result<PipelineLayout, device::OutOfMemory>
928     where
929         Is: Iterator<Item = &'a DescriptorSetLayout>,
930         Ic: Iterator<Item = (pso::ShaderStageFlags, Range<u32>)>,
931     {
932         let mut res_offsets = MultiStageData::<RegisterData<RegisterAccumulator>>::default();
933         let mut sets = Vec::new();
934         for set_layout in set_layouts {
935             sets.push(DescriptorSetInfo {
936                 bindings: Arc::clone(&set_layout.bindings),
937                 registers: res_offsets.advance(&set_layout.pool_mapping),
938             });
939         }
940 
941         res_offsets.map_other(|data| {
942             // These use <= because this tells us the _next_ register, so maximum usage will be equal to the limit.
943             //
944             // Leave one slot for push constants
945             assert!(
946                 data.c.res_index as u32
947                     <= d3d11::D3D11_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT - 1,
948                 "{} bound constant buffers exceeds limit of {}",
949                 data.c.res_index as u32,
950                 d3d11::D3D11_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT - 1,
951             );
952             assert!(
953                 data.s.res_index as u32 <= d3d11::D3D11_COMMONSHADER_SAMPLER_REGISTER_COUNT,
954                 "{} bound samplers exceeds limit of {}",
955                 data.s.res_index as u32,
956                 d3d11::D3D11_COMMONSHADER_SAMPLER_REGISTER_COUNT,
957             );
958             assert!(
959                 data.t.res_index as u32 <= d3d11::D3D11_COMMONSHADER_INPUT_RESOURCE_REGISTER_COUNT,
960                 "{} bound sampled textures and read-only buffers exceeds limit of {}",
961                 data.t.res_index as u32,
962                 d3d11::D3D11_COMMONSHADER_INPUT_RESOURCE_REGISTER_COUNT,
963             );
964             assert!(
965                 data.u.res_index as u32 <= d3d11::D3D11_PS_CS_UAV_REGISTER_COUNT,
966                 "{} bound storage textures and read-write buffers exceeds limit of {}",
967                 data.u.res_index as u32,
968                 d3d11::D3D11_PS_CS_UAV_REGISTER_COUNT,
969             );
970         });
971 
972         Ok(PipelineLayout { sets })
973     }
974 
create_pipeline_cache( &self, _data: Option<&[u8]>, ) -> Result<(), device::OutOfMemory>975     unsafe fn create_pipeline_cache(
976         &self,
977         _data: Option<&[u8]>,
978     ) -> Result<(), device::OutOfMemory> {
979         Ok(())
980     }
981 
get_pipeline_cache_data(&self, _cache: &()) -> Result<Vec<u8>, device::OutOfMemory>982     unsafe fn get_pipeline_cache_data(&self, _cache: &()) -> Result<Vec<u8>, device::OutOfMemory> {
983         //empty
984         Ok(Vec::new())
985     }
986 
destroy_pipeline_cache(&self, _: ())987     unsafe fn destroy_pipeline_cache(&self, _: ()) {
988         //empty
989     }
990 
merge_pipeline_caches<'a, I>( &self, _: &mut (), _: I, ) -> Result<(), device::OutOfMemory> where I: Iterator<Item = &'a ()>,991     unsafe fn merge_pipeline_caches<'a, I>(
992         &self,
993         _: &mut (),
994         _: I,
995     ) -> Result<(), device::OutOfMemory>
996     where
997         I: Iterator<Item = &'a ()>,
998     {
999         //empty
1000         Ok(())
1001     }
1002 
create_graphics_pipeline<'a>( &self, desc: &pso::GraphicsPipelineDesc<'a, Backend>, _cache: Option<&()>, ) -> Result<GraphicsPipeline, pso::CreationError>1003     unsafe fn create_graphics_pipeline<'a>(
1004         &self,
1005         desc: &pso::GraphicsPipelineDesc<'a, Backend>,
1006         _cache: Option<&()>,
1007     ) -> Result<GraphicsPipeline, pso::CreationError> {
1008         let features = &self.features;
1009         let build_shader =
1010             |stage: ShaderStage, source: Option<&pso::EntryPoint<'a, Backend>>| match source {
1011                 Some(src) => Self::extract_entry_point(
1012                     stage,
1013                     src,
1014                     desc.layout,
1015                     features,
1016                     self.internal.device_feature_level,
1017                 ),
1018                 None => Ok(None),
1019             };
1020 
1021         let (layout, vs, gs, hs, ds) = match desc.primitive_assembler {
1022             pso::PrimitiveAssemblerDesc::Vertex {
1023                 buffers,
1024                 attributes,
1025                 ref input_assembler,
1026                 ref vertex,
1027                 ref tessellation,
1028                 ref geometry,
1029             } => {
1030                 let vertex_semantic_remapping = match vertex.module {
1031                     ShaderModule::Spirv(spirv) => {
1032                         shader::introspect_spirv_vertex_semantic_remapping(spirv)?
1033                     }
1034                     _ => unimplemented!(),
1035                 };
1036 
1037                 let vs = build_shader(ShaderStage::Vertex, Some(&vertex))?.unwrap();
1038                 let gs = build_shader(ShaderStage::Geometry, geometry.as_ref())?;
1039 
1040                 let layout = self.create_input_layout(
1041                     vs.clone(),
1042                     buffers,
1043                     attributes,
1044                     input_assembler,
1045                     vertex_semantic_remapping,
1046                 )?;
1047 
1048                 let vs = self.create_vertex_shader(vs)?;
1049                 let gs = if let Some(blob) = gs {
1050                     Some(self.create_geometry_shader(blob)?)
1051                 } else {
1052                     None
1053                 };
1054                 let (hs, ds) = if let Some(ts) = tessellation {
1055                     let hs = build_shader(ShaderStage::Hull, Some(&ts.0))?.unwrap();
1056                     let ds = build_shader(ShaderStage::Domain, Some(&ts.1))?.unwrap();
1057 
1058                     (
1059                         Some(self.create_hull_shader(hs)?),
1060                         Some(self.create_domain_shader(ds)?),
1061                     )
1062                 } else {
1063                     (None, None)
1064                 };
1065 
1066                 (layout, vs, gs, hs, ds)
1067             }
1068             pso::PrimitiveAssemblerDesc::Mesh { .. } => {
1069                 return Err(pso::CreationError::UnsupportedPipeline)
1070             }
1071         };
1072 
1073         let ps = build_shader(ShaderStage::Fragment, desc.fragment.as_ref())?;
1074         let ps = if let Some(blob) = ps {
1075             Some(self.create_pixel_shader(blob)?)
1076         } else {
1077             None
1078         };
1079 
1080         let rasterizer_state =
1081             self.create_rasterizer_state(&desc.rasterizer, &desc.multisampling)?;
1082         let blend_state = self.create_blend_state(&desc.blender, &desc.multisampling)?;
1083         let depth_stencil_state = Some(self.create_depth_stencil_state(&desc.depth_stencil)?);
1084 
1085         match desc.label {
1086             Some(label) if verify_debug_ascii(label) => {
1087                 let mut name = label.to_string();
1088 
1089                 set_debug_name_with_suffix(&blend_state, &mut name, " -- Blend State");
1090                 set_debug_name_with_suffix(&rasterizer_state, &mut name, " -- Rasterizer State");
1091                 set_debug_name_with_suffix(&layout.raw, &mut name, " -- Input Layout");
1092                 if let Some(ref dss) = depth_stencil_state {
1093                     set_debug_name_with_suffix(&dss.raw, &mut name, " -- Depth Stencil State");
1094                 }
1095             }
1096             _ => {}
1097         }
1098 
1099         Ok(GraphicsPipeline {
1100             vs,
1101             gs,
1102             ds,
1103             hs,
1104             ps,
1105             topology: layout.topology,
1106             input_layout: layout.raw,
1107             rasterizer_state,
1108             blend_state,
1109             depth_stencil_state,
1110             baked_states: desc.baked_states.clone(),
1111             required_bindings: layout.required_bindings,
1112             max_vertex_bindings: layout.max_vertex_bindings,
1113             strides: layout.vertex_strides,
1114         })
1115     }
1116 
create_compute_pipeline<'a>( &self, desc: &pso::ComputePipelineDesc<'a, Backend>, _cache: Option<&()>, ) -> Result<ComputePipeline, pso::CreationError>1117     unsafe fn create_compute_pipeline<'a>(
1118         &self,
1119         desc: &pso::ComputePipelineDesc<'a, Backend>,
1120         _cache: Option<&()>,
1121     ) -> Result<ComputePipeline, pso::CreationError> {
1122         let features = &self.features;
1123         let build_shader =
1124             |stage: ShaderStage, source: Option<&pso::EntryPoint<'a, Backend>>| match source {
1125                 Some(src) => Self::extract_entry_point(
1126                     stage,
1127                     src,
1128                     desc.layout,
1129                     features,
1130                     self.internal.device_feature_level,
1131                 ),
1132                 None => Ok(None),
1133             };
1134 
1135         let cs = build_shader(ShaderStage::Compute, Some(&desc.shader))?.unwrap();
1136         let cs = self.create_compute_shader(cs)?;
1137 
1138         Ok(ComputePipeline { cs })
1139     }
1140 
create_framebuffer<I>( &self, _renderpass: &RenderPass, _attachments: I, extent: image::Extent, ) -> Result<Framebuffer, device::OutOfMemory>1141     unsafe fn create_framebuffer<I>(
1142         &self,
1143         _renderpass: &RenderPass,
1144         _attachments: I,
1145         extent: image::Extent,
1146     ) -> Result<Framebuffer, device::OutOfMemory> {
1147         Ok(Framebuffer {
1148             layers: extent.depth as _,
1149         })
1150     }
1151 
create_shader_module( &self, raw_data: &[u32], ) -> Result<ShaderModule, device::ShaderError>1152     unsafe fn create_shader_module(
1153         &self,
1154         raw_data: &[u32],
1155     ) -> Result<ShaderModule, device::ShaderError> {
1156         Ok(ShaderModule::Spirv(raw_data.into()))
1157     }
1158 
create_buffer( &self, size: u64, usage: buffer::Usage, _sparse: memory::SparseFlags, ) -> Result<Buffer, buffer::CreationError>1159     unsafe fn create_buffer(
1160         &self,
1161         size: u64,
1162         usage: buffer::Usage,
1163         _sparse: memory::SparseFlags,
1164     ) -> Result<Buffer, buffer::CreationError> {
1165         use buffer::Usage;
1166 
1167         let mut bind = 0;
1168 
1169         if usage.contains(Usage::UNIFORM) {
1170             bind |= d3d11::D3D11_BIND_CONSTANT_BUFFER;
1171         }
1172         if usage.contains(Usage::VERTEX) {
1173             bind |= d3d11::D3D11_BIND_VERTEX_BUFFER;
1174         }
1175         if usage.contains(Usage::INDEX) {
1176             bind |= d3d11::D3D11_BIND_INDEX_BUFFER;
1177         }
1178 
1179         // TODO: >=11.1
1180         if usage.intersects(
1181             Usage::UNIFORM_TEXEL | Usage::STORAGE_TEXEL | Usage::TRANSFER_SRC | Usage::STORAGE,
1182         ) {
1183             bind |= d3d11::D3D11_BIND_SHADER_RESOURCE;
1184         }
1185 
1186         if usage.intersects(Usage::TRANSFER_DST | Usage::STORAGE) {
1187             bind |= d3d11::D3D11_BIND_UNORDERED_ACCESS;
1188         }
1189 
1190         // if `D3D11_BIND_CONSTANT_BUFFER` intersects with any other bind flag, we need to handle
1191         // it by creating two buffers. one with `D3D11_BIND_CONSTANT_BUFFER` and one with the rest
1192         let needs_disjoint_cb = bind & d3d11::D3D11_BIND_CONSTANT_BUFFER != 0
1193             && bind != d3d11::D3D11_BIND_CONSTANT_BUFFER;
1194 
1195         if needs_disjoint_cb {
1196             bind ^= d3d11::D3D11_BIND_CONSTANT_BUFFER;
1197         }
1198 
1199         fn up_align(x: u64, alignment: u64) -> u64 {
1200             (x + alignment - 1) & !(alignment - 1)
1201         }
1202 
1203         // constant buffer size need to be divisible by 16
1204         let size = if usage.contains(Usage::UNIFORM) {
1205             up_align(size, 16)
1206         } else {
1207             up_align(size, 4)
1208         };
1209 
1210         Ok(Buffer {
1211             internal: InternalBuffer {
1212                 raw: ptr::null_mut(),
1213                 disjoint_cb: if needs_disjoint_cb {
1214                     Some(ptr::null_mut())
1215                 } else {
1216                     None
1217                 },
1218                 srv: None,
1219                 uav: None,
1220                 usage,
1221                 debug_name: None,
1222             },
1223             bound_range: 0..0,
1224             local_memory_arena: Weak::new(),
1225             memory_index: None,
1226             is_coherent: false,
1227             memory_ptr: ptr::null_mut(),
1228             bind,
1229             requirements: memory::Requirements {
1230                 size,
1231                 alignment: 4,
1232                 type_mask: BUFFER_TYPE_MASK,
1233             },
1234         })
1235     }
1236 
get_buffer_requirements(&self, buffer: &Buffer) -> memory::Requirements1237     unsafe fn get_buffer_requirements(&self, buffer: &Buffer) -> memory::Requirements {
1238         buffer.requirements
1239     }
1240 
bind_buffer_memory( &self, memory: &Memory, offset: u64, buffer: &mut Buffer, ) -> Result<(), device::BindError>1241     unsafe fn bind_buffer_memory(
1242         &self,
1243         memory: &Memory,
1244         offset: u64,
1245         buffer: &mut Buffer,
1246     ) -> Result<(), device::BindError> {
1247         debug!(
1248             "usage={:?}, props={:b}",
1249             buffer.internal.usage, memory.properties
1250         );
1251 
1252         #[allow(non_snake_case)]
1253         let mut MiscFlags = if buffer.bind
1254             & (d3d11::D3D11_BIND_SHADER_RESOURCE | d3d11::D3D11_BIND_UNORDERED_ACCESS)
1255             != 0
1256         {
1257             d3d11::D3D11_RESOURCE_MISC_BUFFER_ALLOW_RAW_VIEWS
1258         } else {
1259             0
1260         };
1261 
1262         if buffer.internal.usage.contains(buffer::Usage::INDIRECT) {
1263             MiscFlags |= d3d11::D3D11_RESOURCE_MISC_DRAWINDIRECT_ARGS;
1264         }
1265 
1266         let initial_data = if memory.host_ptr.is_null() {
1267             None
1268         } else {
1269             Some(d3d11::D3D11_SUBRESOURCE_DATA {
1270                 pSysMem: memory.host_ptr.offset(offset as isize) as *const _,
1271                 SysMemPitch: 0,
1272                 SysMemSlicePitch: 0,
1273             })
1274         };
1275 
1276         //TODO: check `memory.properties.contains(memory::Properties::DEVICE_LOCAL)` ?
1277         let raw = {
1278             // device local memory
1279             let desc = d3d11::D3D11_BUFFER_DESC {
1280                 ByteWidth: buffer.requirements.size as _,
1281                 Usage: d3d11::D3D11_USAGE_DEFAULT,
1282                 BindFlags: buffer.bind,
1283                 CPUAccessFlags: 0,
1284                 MiscFlags,
1285                 StructureByteStride: if buffer.internal.usage.contains(buffer::Usage::TRANSFER_SRC)
1286                 {
1287                     4
1288                 } else {
1289                     0
1290                 },
1291             };
1292 
1293             let mut raw: *mut d3d11::ID3D11Buffer = ptr::null_mut();
1294             let hr = self.raw.CreateBuffer(
1295                 &desc,
1296                 initial_data.as_ref().map_or(ptr::null_mut(), |id| id),
1297                 &mut raw as *mut *mut _ as *mut *mut _,
1298             );
1299 
1300             if !winerror::SUCCEEDED(hr) {
1301                 return Err(device::BindError::WrongMemory);
1302             }
1303 
1304             if let Some(ref mut name) = buffer.internal.debug_name {
1305                 set_debug_name(&*raw, name);
1306             }
1307 
1308             ComPtr::from_raw(raw)
1309         };
1310 
1311         let disjoint_cb = if buffer.internal.disjoint_cb.is_some() {
1312             let desc = d3d11::D3D11_BUFFER_DESC {
1313                 ByteWidth: buffer.requirements.size as _,
1314                 Usage: d3d11::D3D11_USAGE_DEFAULT,
1315                 BindFlags: d3d11::D3D11_BIND_CONSTANT_BUFFER,
1316                 CPUAccessFlags: 0,
1317                 MiscFlags: 0,
1318                 StructureByteStride: 0,
1319             };
1320 
1321             let mut disjoint_raw: *mut d3d11::ID3D11Buffer = ptr::null_mut();
1322             let hr = self.raw.CreateBuffer(
1323                 &desc,
1324                 initial_data.as_ref().map_or(ptr::null_mut(), |id| id),
1325                 &mut disjoint_raw as *mut *mut _ as *mut *mut _,
1326             );
1327 
1328             if !winerror::SUCCEEDED(hr) {
1329                 return Err(device::BindError::WrongMemory);
1330             }
1331 
1332             if let Some(ref mut name) = buffer.internal.debug_name {
1333                 set_debug_name_with_suffix(&*disjoint_raw, name, " -- Constant Buffer");
1334             }
1335 
1336             Some(disjoint_raw)
1337         } else {
1338             None
1339         };
1340 
1341         let srv = if buffer.bind & d3d11::D3D11_BIND_SHADER_RESOURCE != 0 {
1342             let mut desc = mem::zeroed::<d3d11::D3D11_SHADER_RESOURCE_VIEW_DESC>();
1343             desc.Format = dxgiformat::DXGI_FORMAT_R32_TYPELESS;
1344             desc.ViewDimension = d3dcommon::D3D11_SRV_DIMENSION_BUFFEREX;
1345             *desc.u.BufferEx_mut() = d3d11::D3D11_BUFFEREX_SRV {
1346                 FirstElement: 0,
1347                 NumElements: buffer.requirements.size as u32 / 4,
1348                 Flags: d3d11::D3D11_BUFFEREX_SRV_FLAG_RAW,
1349             };
1350 
1351             let mut srv: *mut d3d11::ID3D11ShaderResourceView = ptr::null_mut();
1352             let hr = self.raw.CreateShaderResourceView(
1353                 raw.as_raw() as *mut _,
1354                 &desc,
1355                 &mut srv as *mut *mut _ as *mut *mut _,
1356             );
1357 
1358             if !winerror::SUCCEEDED(hr) {
1359                 error!("CreateShaderResourceView failed: 0x{:x}", hr);
1360 
1361                 return Err(device::BindError::WrongMemory);
1362             }
1363 
1364             if let Some(ref mut name) = buffer.internal.debug_name {
1365                 set_debug_name_with_suffix(&*srv, name, " -- SRV");
1366             }
1367 
1368             Some(srv)
1369         } else {
1370             None
1371         };
1372 
1373         let uav = if buffer.bind & d3d11::D3D11_BIND_UNORDERED_ACCESS != 0 {
1374             let mut desc = mem::zeroed::<d3d11::D3D11_UNORDERED_ACCESS_VIEW_DESC>();
1375             desc.Format = dxgiformat::DXGI_FORMAT_R32_TYPELESS;
1376             desc.ViewDimension = d3d11::D3D11_UAV_DIMENSION_BUFFER;
1377             *desc.u.Buffer_mut() = d3d11::D3D11_BUFFER_UAV {
1378                 FirstElement: 0,
1379                 NumElements: buffer.requirements.size as u32 / 4,
1380                 Flags: d3d11::D3D11_BUFFER_UAV_FLAG_RAW,
1381             };
1382 
1383             let mut uav: *mut d3d11::ID3D11UnorderedAccessView = ptr::null_mut();
1384             let hr = self.raw.CreateUnorderedAccessView(
1385                 raw.as_raw() as *mut _,
1386                 &desc,
1387                 &mut uav as *mut *mut _ as *mut *mut _,
1388             );
1389 
1390             if !winerror::SUCCEEDED(hr) {
1391                 error!("CreateUnorderedAccessView failed: 0x{:x}", hr);
1392 
1393                 return Err(device::BindError::WrongMemory);
1394             }
1395 
1396             if let Some(ref mut name) = buffer.internal.debug_name {
1397                 set_debug_name_with_suffix(&*uav, name, " -- UAV");
1398             }
1399 
1400             Some(uav)
1401         } else {
1402             None
1403         };
1404 
1405         let internal = InternalBuffer {
1406             raw: raw.into_raw(),
1407             disjoint_cb,
1408             srv,
1409             uav,
1410             usage: buffer.internal.usage,
1411             debug_name: buffer.internal.debug_name.take(),
1412         };
1413         let range = offset..offset + buffer.requirements.size;
1414 
1415         let memory_index = memory.bind_buffer(range.clone(), internal.clone());
1416 
1417         buffer.internal = internal;
1418         buffer.is_coherent = memory
1419             .properties
1420             .contains(hal::memory::Properties::COHERENT);
1421         buffer.memory_ptr = memory.host_ptr;
1422         buffer.bound_range = range;
1423         buffer.local_memory_arena = Arc::downgrade(&memory.local_buffers);
1424         buffer.memory_index = Some(memory_index);
1425 
1426         Ok(())
1427     }
1428 
create_buffer_view( &self, _buffer: &Buffer, _format: Option<format::Format>, _range: buffer::SubRange, ) -> Result<BufferView, buffer::ViewCreationError>1429     unsafe fn create_buffer_view(
1430         &self,
1431         _buffer: &Buffer,
1432         _format: Option<format::Format>,
1433         _range: buffer::SubRange,
1434     ) -> Result<BufferView, buffer::ViewCreationError> {
1435         unimplemented!()
1436     }
1437 
create_image( &self, kind: image::Kind, mip_levels: image::Level, format: format::Format, _tiling: image::Tiling, usage: image::Usage, _sparse: memory::SparseFlags, view_caps: image::ViewCapabilities, ) -> Result<Image, image::CreationError>1438     unsafe fn create_image(
1439         &self,
1440         kind: image::Kind,
1441         mip_levels: image::Level,
1442         format: format::Format,
1443         _tiling: image::Tiling,
1444         usage: image::Usage,
1445         _sparse: memory::SparseFlags,
1446         view_caps: image::ViewCapabilities,
1447     ) -> Result<Image, image::CreationError> {
1448         let surface_desc = format.base_format().0.desc();
1449         let bytes_per_texel = surface_desc.bits / 8;
1450         let ext = kind.extent();
1451         let size = (ext.width * ext.height * ext.depth) as u64 * bytes_per_texel as u64;
1452 
1453         let bind = conv::map_image_usage(usage, surface_desc, self.internal.device_feature_level);
1454         debug!("{:b}", bind);
1455 
1456         Ok(Image {
1457             internal: InternalImage {
1458                 raw: ptr::null_mut(),
1459                 copy_srv: None,
1460                 srv: None,
1461                 unordered_access_views: Vec::new(),
1462                 depth_stencil_views: Vec::new(),
1463                 render_target_views: Vec::new(),
1464                 debug_name: None,
1465             },
1466             decomposed_format: conv::DecomposedDxgiFormat::UNKNOWN,
1467             kind,
1468             mip_levels,
1469             format,
1470             usage,
1471             view_caps,
1472             bind,
1473             requirements: memory::Requirements {
1474                 size: size,
1475                 alignment: 4,
1476                 type_mask: 0x1, // device-local only
1477             },
1478         })
1479     }
1480 
get_image_requirements(&self, image: &Image) -> memory::Requirements1481     unsafe fn get_image_requirements(&self, image: &Image) -> memory::Requirements {
1482         image.requirements
1483     }
1484 
get_image_subresource_footprint( &self, _image: &Image, _sub: image::Subresource, ) -> image::SubresourceFootprint1485     unsafe fn get_image_subresource_footprint(
1486         &self,
1487         _image: &Image,
1488         _sub: image::Subresource,
1489     ) -> image::SubresourceFootprint {
1490         unimplemented!()
1491     }
1492 
bind_image_memory( &self, memory: &Memory, _offset: u64, image: &mut Image, ) -> Result<(), device::BindError>1493     unsafe fn bind_image_memory(
1494         &self,
1495         memory: &Memory,
1496         _offset: u64,
1497         image: &mut Image,
1498     ) -> Result<(), device::BindError> {
1499         use image::Usage;
1500         use memory::Properties;
1501 
1502         let base_format = image.format.base_format();
1503         let format_desc = base_format.0.desc();
1504 
1505         let compressed = format_desc.is_compressed();
1506         let depth = image.format.is_depth();
1507         let stencil = image.format.is_stencil();
1508 
1509         let (bind, usage, cpu) = if memory.properties == Properties::DEVICE_LOCAL {
1510             (image.bind, d3d11::D3D11_USAGE_DEFAULT, 0)
1511         } else if memory.properties
1512             == (Properties::DEVICE_LOCAL | Properties::CPU_VISIBLE | Properties::CPU_CACHED)
1513         {
1514             (
1515                 image.bind,
1516                 d3d11::D3D11_USAGE_DYNAMIC,
1517                 d3d11::D3D11_CPU_ACCESS_WRITE,
1518             )
1519         } else if memory.properties == (Properties::CPU_VISIBLE | Properties::CPU_CACHED) {
1520             (
1521                 0,
1522                 d3d11::D3D11_USAGE_STAGING,
1523                 d3d11::D3D11_CPU_ACCESS_READ | d3d11::D3D11_CPU_ACCESS_WRITE,
1524             )
1525         } else {
1526             unimplemented!()
1527         };
1528 
1529         let dxgi_format = conv::map_format(image.format).unwrap();
1530         let decomposed = conv::DecomposedDxgiFormat::from_dxgi_format(dxgi_format);
1531         assert!(
1532             memory.host_ptr.is_null(),
1533             "Images can only be allocated from device-local memory"
1534         );
1535         let initial_data_ptr = ptr::null_mut();
1536 
1537         let mut resource = ptr::null_mut();
1538         let view_kind = match image.kind {
1539             image::Kind::D1(width, layers) => {
1540                 let desc = d3d11::D3D11_TEXTURE1D_DESC {
1541                     Width: width,
1542                     MipLevels: image.mip_levels as _,
1543                     ArraySize: layers as _,
1544                     Format: decomposed.typeless,
1545                     Usage: usage,
1546                     BindFlags: bind,
1547                     CPUAccessFlags: cpu,
1548                     MiscFlags: 0,
1549                 };
1550 
1551                 let hr = self.raw.CreateTexture1D(
1552                     &desc,
1553                     initial_data_ptr,
1554                     &mut resource as *mut *mut _ as *mut *mut _,
1555                 );
1556 
1557                 if !winerror::SUCCEEDED(hr) {
1558                     error!("CreateTexture1D failed: 0x{:x}", hr);
1559 
1560                     return Err(device::BindError::WrongMemory);
1561                 }
1562 
1563                 image::ViewKind::D1Array
1564             }
1565             image::Kind::D2(width, height, layers, samples) => {
1566                 let desc = d3d11::D3D11_TEXTURE2D_DESC {
1567                     Width: width,
1568                     Height: height,
1569                     MipLevels: image.mip_levels as _,
1570                     ArraySize: layers as _,
1571                     Format: decomposed.typeless,
1572                     SampleDesc: dxgitype::DXGI_SAMPLE_DESC {
1573                         Count: samples as _,
1574                         Quality: 0,
1575                     },
1576                     Usage: usage,
1577                     BindFlags: bind,
1578                     CPUAccessFlags: cpu,
1579                     MiscFlags: {
1580                         let mut flags = 0;
1581                         if image.view_caps.contains(image::ViewCapabilities::KIND_CUBE) {
1582                             flags |= d3d11::D3D11_RESOURCE_MISC_TEXTURECUBE;
1583                         }
1584                         flags
1585                     },
1586                 };
1587 
1588                 let hr = self.raw.CreateTexture2D(
1589                     &desc,
1590                     initial_data_ptr,
1591                     &mut resource as *mut *mut _ as *mut *mut _,
1592                 );
1593 
1594                 if !winerror::SUCCEEDED(hr) {
1595                     error!("CreateTexture2D failed: 0x{:x}", hr);
1596 
1597                     return Err(device::BindError::WrongMemory);
1598                 }
1599 
1600                 image::ViewKind::D2Array
1601             }
1602             image::Kind::D3(width, height, depth) => {
1603                 let desc = d3d11::D3D11_TEXTURE3D_DESC {
1604                     Width: width,
1605                     Height: height,
1606                     Depth: depth,
1607                     MipLevels: image.mip_levels as _,
1608                     Format: decomposed.typeless,
1609                     Usage: usage,
1610                     BindFlags: bind,
1611                     CPUAccessFlags: cpu,
1612                     MiscFlags: 0,
1613                 };
1614 
1615                 let hr = self.raw.CreateTexture3D(
1616                     &desc,
1617                     initial_data_ptr,
1618                     &mut resource as *mut *mut _ as *mut *mut _,
1619                 );
1620 
1621                 if !winerror::SUCCEEDED(hr) {
1622                     error!("CreateTexture3D failed: 0x{:x}", hr);
1623 
1624                     return Err(device::BindError::WrongMemory);
1625                 }
1626 
1627                 image::ViewKind::D3
1628             }
1629         };
1630 
1631         let mut unordered_access_views = Vec::new();
1632 
1633         if image.usage.contains(Usage::TRANSFER_DST)
1634             && !compressed
1635             && !depth
1636             && self.internal.downlevel.storage_images
1637         {
1638             for mip in 0..image.mip_levels {
1639                 let view = ViewInfo {
1640                     resource: resource,
1641                     kind: image.kind,
1642                     caps: image::ViewCapabilities::empty(),
1643                     view_kind,
1644                     // TODO: we should be using `uav_format` rather than `copy_uav_format`, and share
1645                     //       the UAVs when the formats are identical
1646                     format: decomposed.copy_uav.unwrap(),
1647                     levels: mip..(mip + 1),
1648                     layers: 0..image.kind.num_layers(),
1649                 };
1650 
1651                 let uav = self
1652                     .view_image_as_unordered_access(&view)
1653                     .map_err(|_| device::BindError::WrongMemory)?;
1654 
1655                 if let Some(ref name) = image.internal.debug_name {
1656                     set_debug_name(&uav, &format!("{} -- UAV Mip {}", name, mip));
1657                 }
1658 
1659                 unordered_access_views.push(uav);
1660             }
1661         }
1662 
1663         let (copy_srv, srv) = if image.usage.contains(image::Usage::TRANSFER_SRC) {
1664             let mut view = ViewInfo {
1665                 resource: resource,
1666                 kind: image.kind,
1667                 caps: image::ViewCapabilities::empty(),
1668                 view_kind,
1669                 format: decomposed.copy_srv.unwrap(),
1670                 levels: 0..image.mip_levels,
1671                 layers: 0..image.kind.num_layers(),
1672             };
1673 
1674             let copy_srv = if !compressed {
1675                 Some(
1676                     self.view_image_as_shader_resource(&view)
1677                         .map_err(|_| device::BindError::WrongMemory)?,
1678                 )
1679             } else {
1680                 None
1681             };
1682 
1683             view.format = decomposed.srv.unwrap();
1684 
1685             let srv = if !depth && !stencil {
1686                 Some(
1687                     self.view_image_as_shader_resource(&view)
1688                         .map_err(|_| device::BindError::WrongMemory)?,
1689                 )
1690             } else {
1691                 None
1692             };
1693 
1694             (copy_srv, srv)
1695         } else {
1696             (None, None)
1697         };
1698 
1699         let mut render_target_views = Vec::new();
1700 
1701         if (image.usage.contains(image::Usage::COLOR_ATTACHMENT)
1702             || image.usage.contains(image::Usage::TRANSFER_DST))
1703             && !compressed
1704             && !depth
1705         {
1706             for layer in 0..image.kind.num_layers() {
1707                 for mip in 0..image.mip_levels {
1708                     let view = ViewInfo {
1709                         resource,
1710                         kind: image.kind,
1711                         caps: image::ViewCapabilities::empty(),
1712                         view_kind,
1713                         format: decomposed.rtv.unwrap(),
1714                         levels: mip..(mip + 1),
1715                         layers: layer..(layer + 1),
1716                     };
1717 
1718                     let rtv = self
1719                         .view_image_as_render_target(&view)
1720                         .map_err(|_| device::BindError::WrongMemory)?;
1721 
1722                     if let Some(ref name) = image.internal.debug_name {
1723                         set_debug_name(
1724                             &rtv,
1725                             &format!("{} -- RTV Mip {} Layer {}", name, mip, layer),
1726                         );
1727                     }
1728 
1729                     render_target_views.push(rtv);
1730                 }
1731             }
1732         };
1733 
1734         let mut depth_stencil_views = Vec::new();
1735 
1736         if depth {
1737             for layer in 0..image.kind.num_layers() {
1738                 for mip in 0..image.mip_levels {
1739                     let view = ViewInfo {
1740                         resource,
1741                         kind: image.kind,
1742                         caps: image::ViewCapabilities::empty(),
1743                         view_kind,
1744                         format: decomposed.dsv.unwrap(),
1745                         levels: mip..(mip + 1),
1746                         layers: layer..(layer + 1),
1747                     };
1748 
1749                     let dsv = self
1750                         .view_image_as_depth_stencil(&view, None)
1751                         .map_err(|_| device::BindError::WrongMemory)?;
1752 
1753                     if let Some(ref name) = image.internal.debug_name {
1754                         set_debug_name(
1755                             &dsv,
1756                             &format!("{} -- DSV Mip {} Layer {}", name, mip, layer),
1757                         );
1758                     }
1759 
1760                     depth_stencil_views.push(dsv);
1761                 }
1762             }
1763         }
1764 
1765         if let Some(ref mut name) = image.internal.debug_name {
1766             set_debug_name(&*resource, name);
1767             if let Some(ref copy_srv) = copy_srv {
1768                 set_debug_name_with_suffix(copy_srv, name, " -- Copy SRV");
1769             }
1770             if let Some(ref srv) = srv {
1771                 set_debug_name_with_suffix(srv, name, " -- SRV");
1772             }
1773         }
1774 
1775         let internal = InternalImage {
1776             raw: resource,
1777             copy_srv,
1778             srv,
1779             unordered_access_views,
1780             depth_stencil_views,
1781             render_target_views,
1782             debug_name: image.internal.debug_name.take(),
1783         };
1784 
1785         image.decomposed_format = decomposed;
1786         image.internal = internal;
1787 
1788         Ok(())
1789     }
1790 
create_image_view( &self, image: &Image, view_kind: image::ViewKind, format: format::Format, _swizzle: format::Swizzle, usage: image::Usage, range: image::SubresourceRange, ) -> Result<ImageView, image::ViewCreationError>1791     unsafe fn create_image_view(
1792         &self,
1793         image: &Image,
1794         view_kind: image::ViewKind,
1795         format: format::Format,
1796         _swizzle: format::Swizzle,
1797         usage: image::Usage,
1798         range: image::SubresourceRange,
1799     ) -> Result<ImageView, image::ViewCreationError> {
1800         let is_array = image.kind.num_layers() > 1;
1801         let num_levels = range.resolve_level_count(image.mip_levels);
1802         let num_layers = range.resolve_layer_count(image.kind.num_layers());
1803 
1804         let info = ViewInfo {
1805             resource: image.internal.raw,
1806             kind: image.kind,
1807             caps: image.view_caps,
1808             // D3D11 doesn't allow looking at a single slice of an array as a non-array
1809             view_kind: if is_array && view_kind == image::ViewKind::D2 {
1810                 image::ViewKind::D2Array
1811             } else if is_array && view_kind == image::ViewKind::D1 {
1812                 image::ViewKind::D1Array
1813             } else {
1814                 view_kind
1815             },
1816             format: conv::map_format(format).ok_or(image::ViewCreationError::BadFormat(format))?,
1817             levels: range.level_start..range.level_start + num_levels,
1818             layers: range.layer_start..range.layer_start + num_layers,
1819         };
1820 
1821         let srv_info = ViewInfo {
1822             format: conv::viewable_format(info.format),
1823             ..info.clone()
1824         };
1825 
1826         let mut debug_name = image.internal.debug_name.clone();
1827 
1828         Ok(ImageView {
1829             subresource: d3d11::D3D11CalcSubresource(
1830                 0,
1831                 range.layer_start as _,
1832                 range.level_start as _,
1833             ),
1834             format,
1835             srv_handle: if usage.intersects(image::Usage::SAMPLED) {
1836                 let srv = self.view_image_as_shader_resource(&srv_info)?;
1837 
1838                 if let Some(ref mut name) = debug_name {
1839                     set_debug_name_with_suffix(&srv, name, " -- SRV");
1840                 }
1841 
1842                 Some(srv.into_raw())
1843             } else {
1844                 None
1845             },
1846             rtv_handle: if usage.contains(image::Usage::COLOR_ATTACHMENT) {
1847                 let rtv = self.view_image_as_render_target(&info)?;
1848 
1849                 if let Some(ref mut name) = debug_name {
1850                     set_debug_name_with_suffix(&rtv, name, " -- RTV");
1851                 }
1852 
1853                 Some(rtv.into_raw())
1854             } else {
1855                 None
1856             },
1857             uav_handle: if usage.contains(image::Usage::STORAGE) {
1858                 let uav = self.view_image_as_unordered_access(&info)?;
1859 
1860                 if let Some(ref mut name) = debug_name {
1861                     set_debug_name_with_suffix(&uav, name, " -- UAV");
1862                 }
1863 
1864                 Some(uav.into_raw())
1865             } else {
1866                 None
1867             },
1868             dsv_handle: if usage.contains(image::Usage::DEPTH_STENCIL_ATTACHMENT) {
1869                 if let Some(dsv) = self.view_image_as_depth_stencil(&info, None).ok() {
1870                     if let Some(ref mut name) = debug_name {
1871                         set_debug_name_with_suffix(&dsv, name, " -- DSV");
1872                     }
1873 
1874                     Some(dsv.into_raw())
1875                 } else {
1876                     None
1877                 }
1878             } else {
1879                 None
1880             },
1881             rodsv_handle: if usage.contains(image::Usage::DEPTH_STENCIL_ATTACHMENT)
1882                 && self.internal.downlevel.read_only_depth_stencil
1883             {
1884                 if let Some(rodsv) = self
1885                     .view_image_as_depth_stencil(&info, Some(image.format.is_stencil()))
1886                     .ok()
1887                 {
1888                     if let Some(ref mut name) = debug_name {
1889                         set_debug_name_with_suffix(&rodsv, name, " -- DSV");
1890                     }
1891 
1892                     Some(rodsv.into_raw())
1893                 } else {
1894                     None
1895                 }
1896             } else {
1897                 None
1898             },
1899             owned: true,
1900         })
1901     }
1902 
create_sampler( &self, info: &image::SamplerDesc, ) -> Result<Sampler, device::AllocationError>1903     unsafe fn create_sampler(
1904         &self,
1905         info: &image::SamplerDesc,
1906     ) -> Result<Sampler, device::AllocationError> {
1907         assert!(info.normalized);
1908 
1909         let op = match info.comparison {
1910             Some(_) => d3d11::D3D11_FILTER_REDUCTION_TYPE_COMPARISON,
1911             None => d3d11::D3D11_FILTER_REDUCTION_TYPE_STANDARD,
1912         };
1913 
1914         let desc = d3d11::D3D11_SAMPLER_DESC {
1915             Filter: conv::map_filter(
1916                 info.min_filter,
1917                 info.mag_filter,
1918                 info.mip_filter,
1919                 op,
1920                 info.anisotropy_clamp,
1921             ),
1922             AddressU: conv::map_wrapping(info.wrap_mode.0),
1923             AddressV: conv::map_wrapping(info.wrap_mode.1),
1924             AddressW: conv::map_wrapping(info.wrap_mode.2),
1925             MipLODBias: info.lod_bias.0,
1926             MaxAnisotropy: info.anisotropy_clamp.map_or(0, |aniso| aniso as u32),
1927             ComparisonFunc: info.comparison.map_or(0, |comp| conv::map_comparison(comp)),
1928             BorderColor: info.border.into(),
1929             MinLOD: info.lod_range.start.0,
1930             MaxLOD: info.lod_range.end.0,
1931         };
1932 
1933         let mut sampler = ptr::null_mut();
1934         let hr = self
1935             .raw
1936             .CreateSamplerState(&desc, &mut sampler as *mut *mut _ as *mut *mut _);
1937 
1938         assert_eq!(true, winerror::SUCCEEDED(hr));
1939 
1940         Ok(Sampler {
1941             sampler_handle: ComPtr::from_raw(sampler),
1942         })
1943     }
1944 
create_descriptor_pool<I>( &self, _max_sets: usize, ranges: I, _flags: pso::DescriptorPoolCreateFlags, ) -> Result<DescriptorPool, device::OutOfMemory> where I: Iterator<Item = pso::DescriptorRangeDesc>,1945     unsafe fn create_descriptor_pool<I>(
1946         &self,
1947         _max_sets: usize,
1948         ranges: I,
1949         _flags: pso::DescriptorPoolCreateFlags,
1950     ) -> Result<DescriptorPool, device::OutOfMemory>
1951     where
1952         I: Iterator<Item = pso::DescriptorRangeDesc>,
1953     {
1954         let mut total = RegisterData::default();
1955         for range in ranges {
1956             let content = DescriptorContent::from(range.ty);
1957             total.add_content_many(content, range.count as DescriptorIndex);
1958         }
1959 
1960         let max_stages = 6;
1961         let count = total.sum() * max_stages;
1962         Ok(DescriptorPool::with_capacity(count))
1963     }
1964 
create_descriptor_set_layout<'a, I, J>( &self, layout_bindings: I, _immutable_samplers: J, ) -> Result<DescriptorSetLayout, device::OutOfMemory> where I: Iterator<Item = pso::DescriptorSetLayoutBinding>, J: Iterator<Item = &'a Sampler>,1965     unsafe fn create_descriptor_set_layout<'a, I, J>(
1966         &self,
1967         layout_bindings: I,
1968         _immutable_samplers: J,
1969     ) -> Result<DescriptorSetLayout, device::OutOfMemory>
1970     where
1971         I: Iterator<Item = pso::DescriptorSetLayoutBinding>,
1972         J: Iterator<Item = &'a Sampler>,
1973     {
1974         let mut total = MultiStageData::<RegisterData<_>>::default();
1975         let mut bindings = layout_bindings.collect::<Vec<_>>();
1976 
1977         for binding in bindings.iter() {
1978             let content = DescriptorContent::from(binding.ty);
1979             // If this binding is used by the graphics pipeline and is a UAV, it belongs to the "Output Merger"
1980             // stage, so we only put them in the fragment stage to save redundant descriptor allocations.
1981             let stage_flags = if content.contains(DescriptorContent::UAV)
1982                 && binding
1983                     .stage_flags
1984                     .intersects(pso::ShaderStageFlags::ALL - pso::ShaderStageFlags::COMPUTE)
1985             {
1986                 let mut stage_flags = pso::ShaderStageFlags::FRAGMENT;
1987                 stage_flags.set(
1988                     pso::ShaderStageFlags::COMPUTE,
1989                     binding.stage_flags.contains(pso::ShaderStageFlags::COMPUTE),
1990                 );
1991                 stage_flags
1992             } else {
1993                 binding.stage_flags
1994             };
1995             total.add_content_many(content, stage_flags, binding.count as _);
1996         }
1997 
1998         bindings.sort_by_key(|a| a.binding);
1999 
2000         let accum = total.map_register(|count| RegisterAccumulator {
2001             res_index: *count as ResourceIndex,
2002         });
2003 
2004         Ok(DescriptorSetLayout {
2005             bindings: Arc::new(bindings),
2006             pool_mapping: accum.to_mapping(),
2007         })
2008     }
2009 
write_descriptor_set<'a, I>(&self, op: pso::DescriptorSetWrite<'a, Backend, I>) where I: Iterator<Item = pso::Descriptor<'a, Backend>>,2010     unsafe fn write_descriptor_set<'a, I>(&self, op: pso::DescriptorSetWrite<'a, Backend, I>)
2011     where
2012         I: Iterator<Item = pso::Descriptor<'a, Backend>>,
2013     {
2014         // Get baseline mapping
2015         let mut mapping = op
2016             .set
2017             .layout
2018             .pool_mapping
2019             .map_register(|mapping| mapping.offset);
2020 
2021         // Iterate over layout bindings until the first binding is found.
2022         let binding_start = op
2023             .set
2024             .layout
2025             .bindings
2026             .iter()
2027             .position(|binding| binding.binding == op.binding)
2028             .unwrap();
2029 
2030         // If we've skipped layout bindings, we need to add them to get the correct binding offset
2031         for binding in &op.set.layout.bindings[..binding_start] {
2032             let content = DescriptorContent::from(binding.ty);
2033             mapping.add_content_many(content, binding.stage_flags, binding.count as _);
2034         }
2035 
2036         // We start at the given binding index and array index
2037         let mut binding_index = binding_start;
2038         let mut array_index = op.array_offset;
2039 
2040         // If we're skipping array indices in the current binding, we need to add them to get the correct binding offset
2041         if array_index > 0 {
2042             let binding: &pso::DescriptorSetLayoutBinding = &op.set.layout.bindings[binding_index];
2043             let content = DescriptorContent::from(binding.ty);
2044             mapping.add_content_many(content, binding.stage_flags, array_index as _);
2045         }
2046 
2047         // Iterate over the descriptors, figuring out the corresponding binding, and adding
2048         // it to the set of bindings.
2049         //
2050         // When we hit the end of an array of descriptors and there are still descriptors left
2051         // over, we will spill into writing the next binding.
2052         for descriptor in op.descriptors {
2053             let binding: &pso::DescriptorSetLayoutBinding = &op.set.layout.bindings[binding_index];
2054 
2055             let handles = match descriptor {
2056                 pso::Descriptor::Buffer(buffer, ref _sub) => RegisterData {
2057                     c: match buffer.internal.disjoint_cb {
2058                         Some(dj_buf) => dj_buf as *mut _,
2059                         None => buffer.internal.raw as *mut _,
2060                     },
2061                     t: buffer.internal.srv.map_or(ptr::null_mut(), |p| p as *mut _),
2062                     u: buffer.internal.uav.map_or(ptr::null_mut(), |p| p as *mut _),
2063                     s: ptr::null_mut(),
2064                 },
2065                 pso::Descriptor::Image(image, _layout) => RegisterData {
2066                     c: ptr::null_mut(),
2067                     t: image.srv_handle.map_or(ptr::null_mut(), |h| h as *mut _),
2068                     u: image.uav_handle.map_or(ptr::null_mut(), |h| h as *mut _),
2069                     s: ptr::null_mut(),
2070                 },
2071                 pso::Descriptor::Sampler(sampler) => RegisterData {
2072                     c: ptr::null_mut(),
2073                     t: ptr::null_mut(),
2074                     u: ptr::null_mut(),
2075                     s: sampler.sampler_handle.as_raw() as *mut _,
2076                 },
2077                 pso::Descriptor::CombinedImageSampler(image, _layout, sampler) => RegisterData {
2078                     c: ptr::null_mut(),
2079                     t: image.srv_handle.map_or(ptr::null_mut(), |h| h as *mut _),
2080                     u: image.uav_handle.map_or(ptr::null_mut(), |h| h as *mut _),
2081                     s: sampler.sampler_handle.as_raw() as *mut _,
2082                 },
2083                 pso::Descriptor::TexelBuffer(_buffer_view) => unimplemented!(),
2084             };
2085 
2086             let content = DescriptorContent::from(binding.ty);
2087             if content.contains(DescriptorContent::CBV) {
2088                 let offsets = mapping.map_other(|map| map.c);
2089                 op.set
2090                     .assign_stages(&offsets, binding.stage_flags, handles.c);
2091             };
2092             if content.contains(DescriptorContent::SRV) {
2093                 let offsets = mapping.map_other(|map| map.t);
2094                 op.set
2095                     .assign_stages(&offsets, binding.stage_flags, handles.t);
2096             };
2097             if content.contains(DescriptorContent::UAV) {
2098                 // If this binding is used by the graphics pipeline and is a UAV, it belongs to the "Output Merger"
2099                 // stage, so we only put them in the fragment stage to save redundant descriptor allocations.
2100                 let stage_flags = if binding
2101                     .stage_flags
2102                     .intersects(pso::ShaderStageFlags::ALL - pso::ShaderStageFlags::COMPUTE)
2103                 {
2104                     let mut stage_flags = pso::ShaderStageFlags::FRAGMENT;
2105                     stage_flags.set(
2106                         pso::ShaderStageFlags::COMPUTE,
2107                         binding.stage_flags.contains(pso::ShaderStageFlags::COMPUTE),
2108                     );
2109                     stage_flags
2110                 } else {
2111                     binding.stage_flags
2112                 };
2113 
2114                 let offsets = mapping.map_other(|map| map.u);
2115                 op.set.assign_stages(&offsets, stage_flags, handles.u);
2116             };
2117             if content.contains(DescriptorContent::SAMPLER) {
2118                 let offsets = mapping.map_other(|map| map.s);
2119                 op.set
2120                     .assign_stages(&offsets, binding.stage_flags, handles.s);
2121             };
2122 
2123             mapping.add_content_many(content, binding.stage_flags, 1);
2124 
2125             array_index += 1;
2126             if array_index >= binding.count {
2127                 // We've run out of array to write to, we should overflow to the next binding.
2128                 array_index = 0;
2129                 binding_index += 1;
2130             }
2131         }
2132     }
2133 
copy_descriptor_set<'a>(&self, _op: pso::DescriptorSetCopy<'a, Backend>)2134     unsafe fn copy_descriptor_set<'a>(&self, _op: pso::DescriptorSetCopy<'a, Backend>) {
2135         unimplemented!()
2136         /*
2137         for offset in 0 .. copy.count {
2138             let (dst_ty, dst_handle_offset, dst_second_handle_offset) = copy
2139                 .dst_set
2140                 .get_handle_offset(copy.dst_binding + offset as u32);
2141             let (src_ty, src_handle_offset, src_second_handle_offset) = copy
2142                 .src_set
2143                 .get_handle_offset(copy.src_binding + offset as u32);
2144             assert_eq!(dst_ty, src_ty);
2145 
2146             let dst_handle = copy.dst_set.handles.offset(dst_handle_offset as isize);
2147             let src_handle = copy.dst_set.handles.offset(src_handle_offset as isize);
2148 
2149             match dst_ty {
2150                 pso::DescriptorType::Image {
2151                     ty: pso::ImageDescriptorType::Sampled { with_sampler: true }
2152                 } => {
2153                     let dst_second_handle = copy
2154                         .dst_set
2155                         .handles
2156                         .offset(dst_second_handle_offset as isize);
2157                     let src_second_handle = copy
2158                         .dst_set
2159                         .handles
2160                         .offset(src_second_handle_offset as isize);
2161 
2162                     *dst_handle = *src_handle;
2163                     *dst_second_handle = *src_second_handle;
2164                 }
2165                 _ => *dst_handle = *src_handle,
2166             }
2167         }*/
2168     }
2169 
map_memory( &self, memory: &mut Memory, segment: memory::Segment, ) -> Result<*mut u8, device::MapError>2170     unsafe fn map_memory(
2171         &self,
2172         memory: &mut Memory,
2173         segment: memory::Segment,
2174     ) -> Result<*mut u8, device::MapError> {
2175         Ok(memory.host_ptr.offset(segment.offset as isize))
2176     }
2177 
unmap_memory(&self, _memory: &mut Memory)2178     unsafe fn unmap_memory(&self, _memory: &mut Memory) {
2179         // persistent mapping FTW
2180     }
2181 
flush_mapped_memory_ranges<'a, I>(&self, ranges: I) -> Result<(), device::OutOfMemory> where I: Iterator<Item = (&'a Memory, memory::Segment)>,2182     unsafe fn flush_mapped_memory_ranges<'a, I>(&self, ranges: I) -> Result<(), device::OutOfMemory>
2183     where
2184         I: Iterator<Item = (&'a Memory, memory::Segment)>,
2185     {
2186         let _scope = debug_scope!(&self.context, "FlushMappedRanges");
2187 
2188         // go through every range we wrote to
2189         for (memory, ref segment) in ranges {
2190             let range = memory.resolve(segment);
2191             let _scope = debug_scope!(&self.context, "Range({:?})", range);
2192             memory.flush(&self.context, range);
2193         }
2194 
2195         Ok(())
2196     }
2197 
invalidate_mapped_memory_ranges<'a, I>( &self, ranges: I, ) -> Result<(), device::OutOfMemory> where I: Iterator<Item = (&'a Memory, memory::Segment)>,2198     unsafe fn invalidate_mapped_memory_ranges<'a, I>(
2199         &self,
2200         ranges: I,
2201     ) -> Result<(), device::OutOfMemory>
2202     where
2203         I: Iterator<Item = (&'a Memory, memory::Segment)>,
2204     {
2205         let _scope = debug_scope!(&self.context, "InvalidateMappedRanges");
2206 
2207         // go through every range we want to read from
2208         for (memory, ref segment) in ranges {
2209             let range = memory.resolve(segment);
2210             let _scope = debug_scope!(&self.context, "Range({:?})", range);
2211             memory.invalidate(
2212                 &self.context,
2213                 range,
2214                 self.internal.working_buffer.clone(),
2215                 self.internal.working_buffer_size,
2216             );
2217         }
2218 
2219         Ok(())
2220     }
2221 
create_semaphore(&self) -> Result<Semaphore, device::OutOfMemory>2222     fn create_semaphore(&self) -> Result<Semaphore, device::OutOfMemory> {
2223         // TODO:
2224         Ok(Semaphore)
2225     }
2226 
create_fence(&self, signalled: bool) -> Result<Fence, device::OutOfMemory>2227     fn create_fence(&self, signalled: bool) -> Result<Fence, device::OutOfMemory> {
2228         Ok(Arc::new(RawFence {
2229             mutex: Mutex::new(signalled),
2230             condvar: Condvar::new(),
2231         }))
2232     }
2233 
reset_fence(&self, fence: &mut Fence) -> Result<(), device::OutOfMemory>2234     unsafe fn reset_fence(&self, fence: &mut Fence) -> Result<(), device::OutOfMemory> {
2235         *fence.mutex.lock() = false;
2236         Ok(())
2237     }
2238 
wait_for_fence( &self, fence: &Fence, timeout_ns: u64, ) -> Result<bool, device::WaitError>2239     unsafe fn wait_for_fence(
2240         &self,
2241         fence: &Fence,
2242         timeout_ns: u64,
2243     ) -> Result<bool, device::WaitError> {
2244         use std::time::{Duration, Instant};
2245 
2246         debug!("wait_for_fence {:?} for {} ns", fence, timeout_ns);
2247         let mut guard = fence.mutex.lock();
2248         match timeout_ns {
2249             0 => Ok(*guard),
2250             0xFFFFFFFFFFFFFFFF => {
2251                 while !*guard {
2252                     fence.condvar.wait(&mut guard);
2253                 }
2254                 Ok(true)
2255             }
2256             _ => {
2257                 let total = Duration::from_nanos(timeout_ns as u64);
2258                 let now = Instant::now();
2259                 while !*guard {
2260                     let duration = match total.checked_sub(now.elapsed()) {
2261                         Some(dur) => dur,
2262                         None => return Ok(false),
2263                     };
2264                     let result = fence.condvar.wait_for(&mut guard, duration);
2265                     if result.timed_out() {
2266                         return Ok(false);
2267                     }
2268                 }
2269                 Ok(true)
2270             }
2271         }
2272     }
2273 
get_fence_status(&self, fence: &Fence) -> Result<bool, device::DeviceLost>2274     unsafe fn get_fence_status(&self, fence: &Fence) -> Result<bool, device::DeviceLost> {
2275         Ok(*fence.mutex.lock())
2276     }
2277 
create_event(&self) -> Result<(), device::OutOfMemory>2278     fn create_event(&self) -> Result<(), device::OutOfMemory> {
2279         unimplemented!()
2280     }
2281 
get_event_status(&self, _event: &()) -> Result<bool, device::WaitError>2282     unsafe fn get_event_status(&self, _event: &()) -> Result<bool, device::WaitError> {
2283         unimplemented!()
2284     }
2285 
set_event(&self, _event: &mut ()) -> Result<(), device::OutOfMemory>2286     unsafe fn set_event(&self, _event: &mut ()) -> Result<(), device::OutOfMemory> {
2287         unimplemented!()
2288     }
2289 
reset_event(&self, _event: &mut ()) -> Result<(), device::OutOfMemory>2290     unsafe fn reset_event(&self, _event: &mut ()) -> Result<(), device::OutOfMemory> {
2291         unimplemented!()
2292     }
2293 
free_memory(&self, mut memory: Memory)2294     unsafe fn free_memory(&self, mut memory: Memory) {
2295         if !memory.host_ptr.is_null() {
2296             let _vec =
2297                 Vec::from_raw_parts(memory.host_ptr, memory.size as usize, memory.size as usize);
2298             // let it drop
2299             memory.host_ptr = ptr::null_mut();
2300         }
2301         for (_, (_range, mut internal)) in memory.local_buffers.write().drain() {
2302             internal.release_resources()
2303         }
2304     }
2305 
create_query_pool( &self, _query_ty: query::Type, _count: query::Id, ) -> Result<QueryPool, query::CreationError>2306     unsafe fn create_query_pool(
2307         &self,
2308         _query_ty: query::Type,
2309         _count: query::Id,
2310     ) -> Result<QueryPool, query::CreationError> {
2311         unimplemented!()
2312     }
2313 
destroy_query_pool(&self, _pool: QueryPool)2314     unsafe fn destroy_query_pool(&self, _pool: QueryPool) {
2315         unimplemented!()
2316     }
2317 
get_query_pool_results( &self, _pool: &QueryPool, _queries: Range<query::Id>, _data: &mut [u8], _stride: buffer::Stride, _flags: query::ResultFlags, ) -> Result<bool, device::WaitError>2318     unsafe fn get_query_pool_results(
2319         &self,
2320         _pool: &QueryPool,
2321         _queries: Range<query::Id>,
2322         _data: &mut [u8],
2323         _stride: buffer::Stride,
2324         _flags: query::ResultFlags,
2325     ) -> Result<bool, device::WaitError> {
2326         unimplemented!()
2327     }
2328 
destroy_shader_module(&self, _shader_lib: ShaderModule)2329     unsafe fn destroy_shader_module(&self, _shader_lib: ShaderModule) {}
2330 
destroy_render_pass(&self, _rp: RenderPass)2331     unsafe fn destroy_render_pass(&self, _rp: RenderPass) {
2332         //unimplemented!()
2333     }
2334 
destroy_pipeline_layout(&self, _layout: PipelineLayout)2335     unsafe fn destroy_pipeline_layout(&self, _layout: PipelineLayout) {
2336         //unimplemented!()
2337     }
2338 
destroy_graphics_pipeline(&self, _pipeline: GraphicsPipeline)2339     unsafe fn destroy_graphics_pipeline(&self, _pipeline: GraphicsPipeline) {}
2340 
destroy_compute_pipeline(&self, _pipeline: ComputePipeline)2341     unsafe fn destroy_compute_pipeline(&self, _pipeline: ComputePipeline) {}
2342 
destroy_framebuffer(&self, _fb: Framebuffer)2343     unsafe fn destroy_framebuffer(&self, _fb: Framebuffer) {}
2344 
destroy_buffer(&self, buffer: Buffer)2345     unsafe fn destroy_buffer(&self, buffer: Buffer) {
2346         let mut internal = buffer.internal;
2347 
2348         if internal.raw.is_null() {
2349             return;
2350         }
2351 
2352         let arena_arc = match buffer.local_memory_arena.upgrade() {
2353             Some(arena) => arena,
2354             // Memory is destroyed before the buffer, we've already been destroyed.
2355             None => return,
2356         };
2357         let mut arena = arena_arc.write();
2358 
2359         let memory_index = buffer.memory_index.expect("Buffer's memory index unset");
2360         // Drop the internal stored by the arena on the floor, it owns nothing.
2361         let _ = arena.remove(memory_index);
2362 
2363         // Release all memory owned by this buffer
2364         internal.release_resources();
2365     }
2366 
destroy_buffer_view(&self, _view: BufferView)2367     unsafe fn destroy_buffer_view(&self, _view: BufferView) {
2368         //unimplemented!()
2369     }
2370 
destroy_image(&self, mut image: Image)2371     unsafe fn destroy_image(&self, mut image: Image) {
2372         image.internal.release_resources();
2373     }
2374 
destroy_image_view(&self, _view: ImageView)2375     unsafe fn destroy_image_view(&self, _view: ImageView) {
2376         //unimplemented!()
2377     }
2378 
destroy_sampler(&self, _sampler: Sampler)2379     unsafe fn destroy_sampler(&self, _sampler: Sampler) {}
2380 
destroy_descriptor_pool(&self, _pool: DescriptorPool)2381     unsafe fn destroy_descriptor_pool(&self, _pool: DescriptorPool) {
2382         //unimplemented!()
2383     }
2384 
destroy_descriptor_set_layout(&self, _layout: DescriptorSetLayout)2385     unsafe fn destroy_descriptor_set_layout(&self, _layout: DescriptorSetLayout) {
2386         //unimplemented!()
2387     }
2388 
destroy_fence(&self, _fence: Fence)2389     unsafe fn destroy_fence(&self, _fence: Fence) {
2390         // unimplemented!()
2391     }
2392 
destroy_semaphore(&self, _semaphore: Semaphore)2393     unsafe fn destroy_semaphore(&self, _semaphore: Semaphore) {
2394         //unimplemented!()
2395     }
2396 
destroy_event(&self, _event: ())2397     unsafe fn destroy_event(&self, _event: ()) {
2398         //unimplemented!()
2399     }
2400 
wait_idle(&self) -> Result<(), device::OutOfMemory>2401     fn wait_idle(&self) -> Result<(), device::OutOfMemory> {
2402         Ok(())
2403         // unimplemented!()
2404     }
2405 
set_image_name(&self, image: &mut Image, name: &str)2406     unsafe fn set_image_name(&self, image: &mut Image, name: &str) {
2407         if !verify_debug_ascii(name) {
2408             return;
2409         }
2410 
2411         image.internal.debug_name = Some(name.to_string());
2412     }
2413 
set_buffer_name(&self, buffer: &mut Buffer, name: &str)2414     unsafe fn set_buffer_name(&self, buffer: &mut Buffer, name: &str) {
2415         if !verify_debug_ascii(name) {
2416             return;
2417         }
2418 
2419         buffer.internal.debug_name = Some(name.to_string());
2420     }
2421 
set_command_buffer_name(&self, command_buffer: &mut CommandBuffer, name: &str)2422     unsafe fn set_command_buffer_name(&self, command_buffer: &mut CommandBuffer, name: &str) {
2423         if !verify_debug_ascii(name) {
2424             return;
2425         }
2426 
2427         command_buffer.debug_name = Some(name.to_string());
2428     }
2429 
set_semaphore_name(&self, _semaphore: &mut Semaphore, _name: &str)2430     unsafe fn set_semaphore_name(&self, _semaphore: &mut Semaphore, _name: &str) {
2431         // TODO
2432     }
2433 
set_fence_name(&self, _fence: &mut Fence, _name: &str)2434     unsafe fn set_fence_name(&self, _fence: &mut Fence, _name: &str) {
2435         // TODO
2436     }
2437 
set_framebuffer_name(&self, _framebuffer: &mut Framebuffer, _name: &str)2438     unsafe fn set_framebuffer_name(&self, _framebuffer: &mut Framebuffer, _name: &str) {
2439         // TODO
2440     }
2441 
set_render_pass_name(&self, _render_pass: &mut RenderPass, _name: &str)2442     unsafe fn set_render_pass_name(&self, _render_pass: &mut RenderPass, _name: &str) {
2443         // TODO
2444     }
2445 
set_descriptor_set_name(&self, _descriptor_set: &mut DescriptorSet, _name: &str)2446     unsafe fn set_descriptor_set_name(&self, _descriptor_set: &mut DescriptorSet, _name: &str) {
2447         // TODO
2448     }
2449 
set_descriptor_set_layout_name( &self, _descriptor_set_layout: &mut DescriptorSetLayout, _name: &str, )2450     unsafe fn set_descriptor_set_layout_name(
2451         &self,
2452         _descriptor_set_layout: &mut DescriptorSetLayout,
2453         _name: &str,
2454     ) {
2455         // TODO
2456     }
2457 
set_pipeline_layout_name(&self, _pipeline_layout: &mut PipelineLayout, _name: &str)2458     unsafe fn set_pipeline_layout_name(&self, _pipeline_layout: &mut PipelineLayout, _name: &str) {
2459         // TODO
2460     }
2461 
start_capture(&self)2462     fn start_capture(&self) {
2463         //TODO
2464     }
2465 
stop_capture(&self)2466     fn stop_capture(&self) {
2467         //TODO
2468     }
2469 }
2470