Merge pull request #1 from MaikKlein/master

Update from master
This commit is contained in:
Graham Wihlidal 2019-02-09 21:11:37 +01:00 committed by GitHub
commit 7ffb94004d
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
39 changed files with 16824 additions and 4438 deletions

View file

@ -1,9 +1,27 @@
os:
- linux
- osx
language: rust language: rust
before_script:
- rustup component add rustfmt
rust: rust:
- stable - stable
script: script:
- cargo fmt --all -- --check
- cargo build --manifest-path ash/Cargo.toml - cargo build --manifest-path ash/Cargo.toml
- cargo build --manifest-path examples/Cargo.toml - cargo build --manifest-path examples/Cargo.toml
- cargo build --manifest-path generator/Cargo.toml - cargo build --manifest-path generator/Cargo.toml
branches:
only:
# This is where pull requests from "bors r+" are built.
- staging
# This is where pull requests from "bors try" are built.
- trying
# Uncomment this to enable building pull requests.
- master

View file

@ -1,3 +1,19 @@
# 0.27.0/1
* Extensions are now namespaced. `ash::extensions::khr::Swapchain`
* Removed vendor tags from extension methods
* Added missing functions for VkEvent
* The examples were updated to use the new builder pattern
* A SPIR-V parsing function `ash::util::read_spv`
* Added `get_pipeline_cache_data`
# 0.26.0
* Fix loader on MacOS.
* Expose function pointers for easier interop with external libraries.
* Builder now uses bool instead of Bool32.
# 0.25.0 # 0.25.0
* Adds support for Vulkan 1.1 * Adds support for Vulkan 1.1

View file

@ -36,9 +36,9 @@ let instance = entry.create_instance(&create_info, None)
### `Vec<T>` instead of mutable slices ### `Vec<T>` instead of mutable slices
```Rust ```Rust
pub fn get_swapchain_images_khr(&self, pub fn get_swapchain_images(&self,
swapchain: vk::SwapchainKHR) swapchain: vk::SwapchainKHR)
-> VkResult<Vec<vk::Image>>; -> VkResult<Vec<vk::Image>>;
let present_images = swapchain_loader.get_swapchain_images_khr(swapchain).unwrap(); let present_images = swapchain_loader.get_swapchain_images_khr(swapchain).unwrap();
``` ```
*Note*: Functions don't return `Vec<T>` if this would limit the functionality. See `p_next`. *Note*: Functions don't return `Vec<T>` if this would limit the functionality. See `p_next`.
@ -55,6 +55,12 @@ pub fn cmd_pipeline_barrier(&self,
image_memory_barriers: &[vk::ImageMemoryBarrier]); image_memory_barriers: &[vk::ImageMemoryBarrier]);
``` ```
### Strongly typed handles
Each Vulkan handle type is exposed as a newtyped struct for improved type safety. Null handles can be constructed with
`T::null()`, and handles may be freely converted to and from `u64` with `Handle::from_raw` and `Handle::as_raw` for
interop with non-Ash Vulkan code.
### Default implementation for all types ### Default implementation for all types
```Rust ```Rust
// No need to manually set the structure type // No need to manually set the structure type
@ -71,7 +77,11 @@ let pipeline_vertex_input_state_create_info = vk::PipelineVertexInputStateCreate
.vertex_binding_descriptions(&Vertex::binding_descriptions()) .vertex_binding_descriptions(&Vertex::binding_descriptions())
.vertex_attribute_descriptions(&Vertex::attribute_descriptions()).build(); .vertex_attribute_descriptions(&Vertex::attribute_descriptions()).build();
``` ```
*Note*: No validation is done, the lifetimes only have to live as long as the builder object. It is the responsibility of the user to make sure that the pointers are valid.
Builders implement `Deref` targeting their corresponding Vulkan struct, so references to builders can be passed directly
to Vulkan functions. This is encouraged as doing so allows Rust to check the lifetimes of captured objects are valid,
whereas calling `build` discards lifetime information, making inadvertent use-after-free errors more likely.
### Flags and constants as associated constants ### Flags and constants as associated constants
```Rust ```Rust
@ -95,12 +105,6 @@ println!("Display: {}", flag);
// Display: COLOR_ATTACHMENT_READ | COLOR_ATTACHMENT_WRITE // Display: COLOR_ATTACHMENT_READ | COLOR_ATTACHMENT_WRITE
``` ```
### Interop
Vulkan objects inside Ash can be constructed from raw values with `Object::from:raw`. Useful if you need to interact with a C library.
```Rust
PipelineBindPoint::from_raw(bindpoint);
```
### Function pointer loading ### Function pointer loading
Ash also takes care of loading the function pointers. Function pointers are split into 3 categories. Ash also takes care of loading the function pointers. Function pointers are split into 3 categories.
@ -119,9 +123,9 @@ Custom loaders can be implemented.
### Extension loading ### Extension loading
Additionally, every Vulkan extension has to be loaded explicitly. You can find all extensions under [ash::extensions](https://github.com/MaikKlein/ash/tree/master/ash/src/extensions). Additionally, every Vulkan extension has to be loaded explicitly. You can find all extensions under [ash::extensions](https://github.com/MaikKlein/ash/tree/master/ash/src/extensions).
```Rust ```Rust
use ash::extensions::Swapchain; use ash::extensions::khr::Swapchain;
let swapchain_loader = Swapchain::new(&instance, &device); let swapchain_loader = Swapchain::new(&instance, &device);
let swapchain = swapchain_loader.create_swapchain_khr(&swapchain_create_info).unwrap(); let swapchain = swapchain_loader.create_swapchain(&swapchain_create_info).unwrap();
``` ```
### Raw function pointers ### Raw function pointers

View file

@ -1,15 +1,21 @@
os: Visual Studio 2015
environment: environment:
matrix: matrix:
- TARGET: 1.28.0-x86_64-pc-windows # Stable 64-bit MSVC
COMPILER: msvc - channel: stable
target: x86_64-pc-windows-msvc
install: install:
- if %COMPILER%==gnu choco install -y mingw - appveyor DownloadFile https://win.rustup.rs/ -FileName rustup-init.exe
- ps: Start-FileDownload "https://static.rust-lang.org/dist/rust-${env:TARGET}-${env:COMPILER}.exe" -FileName "rust-install.exe" - rustup-init -yv --default-toolchain %channel% --default-host %target%
- ps: .\rust-install.exe /VERYSILENT /NORESTART /DIR="C:\rust" | Out-Null - set PATH=%PATH%;%USERPROFILE%\.cargo\bin
- ps: $env:PATH="$env:PATH;C:\rust\bin;C:\tools\mingw64\bin"
- if %COMPILER%==gnu gcc -v
- rustc -vV - rustc -vV
- cargo -vV - cargo -vV
build_script:
- cargo build --manifest-path ash/Cargo.toml # 'cargo test' takes care of building for us, so disable Appveyor's build stage. This prevents
- cargo build --manifest-path examples/Cargo.toml # the "directory does not contain a project or solution file" error.
build: off
test_script:
- cargo test --verbose %cargoflags%

View file

@ -1,6 +1,6 @@
[package] [package]
name = "ash" name = "ash"
version = "0.25.0" version = "0.27.1"
authors = ["maik klein <maikklein@googlemail.com>"] authors = ["maik klein <maikklein@googlemail.com>"]
description = "Vulkan bindings for Rust" description = "Vulkan bindings for Rust"
license = "MIT" license = "MIT"
@ -11,7 +11,7 @@ documentation = "https://docs.rs/ash"
[dependencies] [dependencies]
shared_library = "0.1.9" shared_library = "0.1.9"
lazy_static = "0.2.1" lazy_static = "1"
[features] [features]
default = [] default = []

View file

@ -51,11 +51,7 @@ pub trait DeviceV1_1: DeviceV1_0 {
peer_memory_features peer_memory_features
} }
unsafe fn cmd_set_device_mask( unsafe fn cmd_set_device_mask(&self, command_buffer: vk::CommandBuffer, device_mask: u32) {
&self,
command_buffer: vk::CommandBuffer,
device_mask: u32,
) {
self.fp_v1_1() self.fp_v1_1()
.cmd_set_device_mask(command_buffer, device_mask); .cmd_set_device_mask(command_buffer, device_mask);
} }
@ -86,11 +82,8 @@ pub trait DeviceV1_1: DeviceV1_0 {
info: &vk::ImageMemoryRequirementsInfo2, info: &vk::ImageMemoryRequirementsInfo2,
out: &mut vk::MemoryRequirements2, out: &mut vk::MemoryRequirements2,
) { ) {
self.fp_v1_1().get_image_memory_requirements2( self.fp_v1_1()
self.handle(), .get_image_memory_requirements2(self.handle(), info, out);
info,
out,
);
} }
unsafe fn get_buffer_memory_requirements2( unsafe fn get_buffer_memory_requirements2(
@ -98,11 +91,8 @@ pub trait DeviceV1_1: DeviceV1_0 {
info: &vk::BufferMemoryRequirementsInfo2, info: &vk::BufferMemoryRequirementsInfo2,
out: &mut vk::MemoryRequirements2, out: &mut vk::MemoryRequirements2,
) { ) {
self.fp_v1_1().get_buffer_memory_requirements2( self.fp_v1_1()
self.handle(), .get_buffer_memory_requirements2(self.handle(), info, out);
info,
out,
);
} }
unsafe fn get_image_sparse_memory_requirements2_len( unsafe fn get_image_sparse_memory_requirements2_len(
@ -221,11 +211,8 @@ pub trait DeviceV1_1: DeviceV1_0 {
create_info: &vk::DescriptorSetLayoutCreateInfo, create_info: &vk::DescriptorSetLayoutCreateInfo,
out: &mut vk::DescriptorSetLayoutSupport, out: &mut vk::DescriptorSetLayoutSupport,
) { ) {
self.fp_v1_1().get_descriptor_set_layout_support( self.fp_v1_1()
self.handle(), .get_descriptor_set_layout_support(self.handle(), create_info, out);
create_info,
out,
);
} }
} }
@ -269,6 +256,94 @@ pub trait DeviceV1_0 {
); );
} }
unsafe fn create_event(
&self,
create_info: &vk::EventCreateInfo,
allocation_callbacks: Option<&vk::AllocationCallbacks>,
) -> VkResult<vk::Event> {
let mut event = mem::uninitialized();
let err_code = self.fp_v1_0().create_event(
self.handle(),
create_info,
allocation_callbacks.as_raw_ptr(),
&mut event,
);
match err_code {
vk::Result::SUCCESS => Ok(event),
_ => Err(err_code),
}
}
/// Returns true if the event was set, and false if the event was reset, otherwise it will
/// return the error code.
unsafe fn get_event_status(&self, event: vk::Event) -> VkResult<bool> {
let err_code = self.fp_v1_0().get_event_status(self.handle(), event);
match err_code {
vk::Result::EVENT_SET => Ok(true),
vk::Result::EVENT_RESET => Ok(false),
_ => Err(err_code),
}
}
unsafe fn set_event(&self, event: vk::Event) -> VkResult<()> {
let err_code = self.fp_v1_0().set_event(self.handle(), event);
match err_code {
vk::Result::SUCCESS => Ok(()),
_ => Err(err_code),
}
}
unsafe fn reset_event(&self, event: vk::Event) -> VkResult<()> {
let err_code = self.fp_v1_0().reset_event(self.handle(), event);
match err_code {
vk::Result::SUCCESS => Ok(()),
_ => Err(err_code),
}
}
unsafe fn cmd_set_event(
&self,
command_buffer: vk::CommandBuffer,
event: vk::Event,
stage_mask: vk::PipelineStageFlags,
) {
self.fp_v1_0()
.cmd_set_event(command_buffer, event, stage_mask);
}
unsafe fn cmd_reset_event(
&self,
command_buffer: vk::CommandBuffer,
event: vk::Event,
stage_mask: vk::PipelineStageFlags,
) {
self.fp_v1_0()
.cmd_reset_event(command_buffer, event, stage_mask);
}
unsafe fn cmd_wait_events(
&self,
command_buffer: vk::CommandBuffer,
events: &[vk::Event],
src_stage_mask: vk::PipelineStageFlags,
dst_stage_mask: vk::PipelineStageFlags,
memory_barriers: &[vk::MemoryBarrier],
buffer_memory_barriers: &[vk::BufferMemoryBarrier],
image_memory_barriers: &[vk::ImageMemoryBarrier],
) {
self.fp_v1_0().cmd_wait_events(
command_buffer,
events.len() as _,
events.as_ptr(),
src_stage_mask,
dst_stage_mask,
memory_barriers.len() as _,
memory_barriers.as_ptr(),
buffer_memory_barriers.len() as _,
buffer_memory_barriers.as_ptr(),
image_memory_barriers.len() as _,
image_memory_barriers.as_ptr(),
);
}
unsafe fn destroy_fence( unsafe fn destroy_fence(
&self, &self,
fence: vk::Fence, fence: vk::Fence,
@ -278,6 +353,15 @@ pub trait DeviceV1_0 {
.destroy_fence(self.handle(), fence, allocation_callbacks.as_raw_ptr()); .destroy_fence(self.handle(), fence, allocation_callbacks.as_raw_ptr());
} }
unsafe fn destroy_event(
&self,
event: vk::Event,
allocation_callbacks: Option<&vk::AllocationCallbacks>,
) {
self.fp_v1_0()
.destroy_event(self.handle(), event, allocation_callbacks.as_raw_ptr());
}
unsafe fn destroy_image( unsafe fn destroy_image(
&self, &self,
image: vk::Image, image: vk::Image,
@ -721,11 +805,9 @@ pub trait DeviceV1_0 {
} }
unsafe fn reset_fences(&self, fences: &[vk::Fence]) -> VkResult<()> { unsafe fn reset_fences(&self, fences: &[vk::Fence]) -> VkResult<()> {
let err_code = self.fp_v1_0().reset_fences( let err_code =
self.handle(), self.fp_v1_0()
fences.len() as u32, .reset_fences(self.handle(), fences.len() as u32, fences.as_ptr());
fences.as_ptr(),
);
match err_code { match err_code {
vk::Result::SUCCESS => Ok(()), vk::Result::SUCCESS => Ok(()),
_ => Err(err_code), _ => Err(err_code),
@ -1291,6 +1373,34 @@ pub trait DeviceV1_0 {
} }
} }
unsafe fn get_pipeline_cache_data(
&self,
pipeline_cache: vk::PipelineCache,
) -> VkResult<Vec<u8>> {
let mut data_size: usize = 0;
let err_code = self.fp_v1_0().get_pipeline_cache_data(
self.handle(),
pipeline_cache,
&mut data_size,
ptr::null_mut(),
);
if err_code != vk::Result::SUCCESS {
return Err(err_code);
};
let mut data: Vec<u8> = Vec::with_capacity(data_size);
let err_code = self.fp_v1_0().get_pipeline_cache_data(
self.handle(),
pipeline_cache,
&mut data_size,
data.as_mut_ptr() as _,
);
data.set_len(data_size);
match err_code {
vk::Result::SUCCESS => Ok(data),
_ => Err(err_code),
}
}
unsafe fn map_memory( unsafe fn map_memory(
&self, &self,
memory: vk::DeviceMemory, memory: vk::DeviceMemory,
@ -1357,11 +1467,7 @@ pub trait DeviceV1_0 {
} }
} }
unsafe fn get_device_queue( unsafe fn get_device_queue(&self, queue_family_index: u32, queue_index: u32) -> vk::Queue {
&self,
queue_family_index: u32,
queue_index: u32,
) -> vk::Queue {
let mut queue = mem::uninitialized(); let mut queue = mem::uninitialized();
self.fp_v1_0() self.fp_v1_0()
.get_device_queue(self.handle(), queue_family_index, queue_index, &mut queue); .get_device_queue(self.handle(), queue_family_index, queue_index, &mut queue);
@ -1413,11 +1519,11 @@ pub trait DeviceV1_0 {
unsafe fn begin_command_buffer( unsafe fn begin_command_buffer(
&self, &self,
command_buffer: vk::CommandBuffer, command_buffer: vk::CommandBuffer,
create_info: &vk::CommandBufferBeginInfo, begin_info: &vk::CommandBufferBeginInfo,
) -> VkResult<()> { ) -> VkResult<()> {
let err_code = self let err_code = self
.fp_v1_0() .fp_v1_0()
.begin_command_buffer(command_buffer, create_info); .begin_command_buffer(command_buffer, begin_info);
match err_code { match err_code {
vk::Result::SUCCESS => Ok(()), vk::Result::SUCCESS => Ok(()),
_ => Err(err_code), _ => Err(err_code),
@ -1473,12 +1579,9 @@ pub trait DeviceV1_0 {
submits: &[vk::SubmitInfo], submits: &[vk::SubmitInfo],
fence: vk::Fence, fence: vk::Fence,
) -> VkResult<()> { ) -> VkResult<()> {
let err_code = self.fp_v1_0().queue_submit( let err_code =
queue, self.fp_v1_0()
submits.len() as u32, .queue_submit(queue, submits.len() as u32, submits.as_ptr(), fence);
submits.as_ptr(),
fence,
);
match err_code { match err_code {
vk::Result::SUCCESS => Ok(()), vk::Result::SUCCESS => Ok(()),
_ => Err(err_code), _ => Err(err_code),
@ -1725,10 +1828,7 @@ pub struct Device {
device_fn_1_1: vk::DeviceFnV1_1, device_fn_1_1: vk::DeviceFnV1_1,
} }
impl Device { impl Device {
pub unsafe fn load( pub unsafe fn load(instance_fn: &vk::InstanceFnV1_0, device: vk::Device) -> Self {
instance_fn: &vk::InstanceFnV1_0,
device: vk::Device,
) -> Self {
let device_fn_1_0 = vk::DeviceFnV1_0::load(|name| { let device_fn_1_0 = vk::DeviceFnV1_0::load(|name| {
mem::transmute(instance_fn.get_device_proc_addr(device, name.as_ptr())) mem::transmute(instance_fn.get_device_proc_addr(device, name.as_ptr()))
}); });

View file

@ -15,25 +15,17 @@ use RawPtr;
#[cfg(windows)] #[cfg(windows)]
const LIB_PATH: &'static str = "vulkan-1.dll"; const LIB_PATH: &'static str = "vulkan-1.dll";
#[cfg( #[cfg(all(
all( unix,
unix, not(any(target_os = "macos", target_os = "ios", target_os = "android"))
not( ))]
any(
target_os = "macos",
target_os = "ios",
target_os = "android"
)
)
)
)]
const LIB_PATH: &'static str = "libvulkan.so.1"; const LIB_PATH: &'static str = "libvulkan.so.1";
#[cfg(target_os = "android")] #[cfg(target_os = "android")]
const LIB_PATH: &'static str = "libvulkan.so"; const LIB_PATH: &'static str = "libvulkan.so";
#[cfg(any(target_os = "macos", target_os = "ios"))] #[cfg(any(target_os = "macos", target_os = "ios"))]
const LIB_PATH: &'static str = "libMoltenVK.dylib"; const LIB_PATH: &'static str = "libvulkan.dylib";
lazy_static! { lazy_static! {
static ref VK_LIB: Result<DynamicLibrary, String> = static ref VK_LIB: Result<DynamicLibrary, String> =
@ -73,7 +65,7 @@ impl Error for InstanceError {
fn cause(&self) -> Option<&Error> { fn cause(&self) -> Option<&Error> {
if let &InstanceError::VkError(ref err) = self { if let &InstanceError::VkError(ref err) = self {
return err.cause(); return err.source();
} }
None None
} }

View file

@ -11,10 +11,7 @@ pub struct DebugMarker {
} }
impl DebugMarker { impl DebugMarker {
pub fn new<I: InstanceV1_0, D: DeviceV1_0>( pub fn new<I: InstanceV1_0, D: DeviceV1_0>(instance: &I, device: &D) -> DebugMarker {
instance: &I,
device: &D,
) -> DebugMarker {
let debug_marker_fn = vk::ExtDebugMarkerFn::load(|name| unsafe { let debug_marker_fn = vk::ExtDebugMarkerFn::load(|name| unsafe {
mem::transmute(instance.get_device_proc_addr(device.handle(), name.as_ptr())) mem::transmute(instance.get_device_proc_addr(device.handle(), name.as_ptr()))
}); });
@ -27,7 +24,7 @@ impl DebugMarker {
CStr::from_bytes_with_nul(b"VK_EXT_debug_marker\0").expect("Wrong extension string") CStr::from_bytes_with_nul(b"VK_EXT_debug_marker\0").expect("Wrong extension string")
} }
pub unsafe fn debug_marker_set_object_name_ext( pub unsafe fn debug_marker_set_object_name(
&self, &self,
device: vk::Device, device: vk::Device,
name_info: &vk::DebugMarkerObjectNameInfoEXT, name_info: &vk::DebugMarkerObjectNameInfoEXT,
@ -41,7 +38,7 @@ impl DebugMarker {
} }
} }
pub unsafe fn cmd_debug_marker_begin_ext( pub unsafe fn cmd_debug_marker_begin(
&self, &self,
command_buffer: vk::CommandBuffer, command_buffer: vk::CommandBuffer,
marker_info: &vk::DebugMarkerMarkerInfoEXT, marker_info: &vk::DebugMarkerMarkerInfoEXT,
@ -50,12 +47,12 @@ impl DebugMarker {
.cmd_debug_marker_begin_ext(command_buffer, marker_info); .cmd_debug_marker_begin_ext(command_buffer, marker_info);
} }
pub unsafe fn cmd_debug_marker_end_ext(&self, command_buffer: vk::CommandBuffer) { pub unsafe fn cmd_debug_marker_end(&self, command_buffer: vk::CommandBuffer) {
self.debug_marker_fn self.debug_marker_fn
.cmd_debug_marker_end_ext(command_buffer); .cmd_debug_marker_end_ext(command_buffer);
} }
pub unsafe fn cmd_debug_marker_insert_ext( pub unsafe fn cmd_debug_marker_insert(
&self, &self,
command_buffer: vk::CommandBuffer, command_buffer: vk::CommandBuffer,
marker_info: &vk::DebugMarkerMarkerInfoEXT, marker_info: &vk::DebugMarkerMarkerInfoEXT,

View file

@ -13,10 +13,7 @@ pub struct DebugReport {
} }
impl DebugReport { impl DebugReport {
pub fn new<E: EntryV1_0, I: InstanceV1_0>( pub fn new<E: EntryV1_0, I: InstanceV1_0>(entry: &E, instance: &I) -> DebugReport {
entry: &E,
instance: &I,
) -> DebugReport {
let debug_report_fn = vk::ExtDebugReportFn::load(|name| unsafe { let debug_report_fn = vk::ExtDebugReportFn::load(|name| unsafe {
mem::transmute(entry.get_instance_proc_addr(instance.handle(), name.as_ptr())) mem::transmute(entry.get_instance_proc_addr(instance.handle(), name.as_ptr()))
}); });
@ -30,7 +27,7 @@ impl DebugReport {
CStr::from_bytes_with_nul(b"VK_EXT_debug_report\0").expect("Wrong extension string") CStr::from_bytes_with_nul(b"VK_EXT_debug_report\0").expect("Wrong extension string")
} }
pub unsafe fn destroy_debug_report_callback_ext( pub unsafe fn destroy_debug_report_callback(
&self, &self,
debug: vk::DebugReportCallbackEXT, debug: vk::DebugReportCallbackEXT,
allocation_callbacks: Option<&vk::AllocationCallbacks>, allocation_callbacks: Option<&vk::AllocationCallbacks>,
@ -42,7 +39,7 @@ impl DebugReport {
); );
} }
pub unsafe fn create_debug_report_callback_ext( pub unsafe fn create_debug_report_callback(
&self, &self,
create_info: &vk::DebugReportCallbackCreateInfoEXT, create_info: &vk::DebugReportCallbackCreateInfoEXT,
allocation_callbacks: Option<&vk::AllocationCallbacks>, allocation_callbacks: Option<&vk::AllocationCallbacks>,

View file

@ -12,10 +12,7 @@ pub struct DebugUtils {
} }
impl DebugUtils { impl DebugUtils {
pub fn new<E: EntryV1_0, I: InstanceV1_0>( pub fn new<E: EntryV1_0, I: InstanceV1_0>(entry: &E, instance: &I) -> DebugUtils {
entry: &E,
instance: &I,
) -> DebugUtils {
let debug_utils_fn = vk::ExtDebugUtilsFn::load(|name| unsafe { let debug_utils_fn = vk::ExtDebugUtilsFn::load(|name| unsafe {
mem::transmute(entry.get_instance_proc_addr(instance.handle(), name.as_ptr())) mem::transmute(entry.get_instance_proc_addr(instance.handle(), name.as_ptr()))
}); });
@ -29,31 +26,35 @@ impl DebugUtils {
CStr::from_bytes_with_nul(b"VK_EXT_debug_utils\0").expect("Wrong extension string") CStr::from_bytes_with_nul(b"VK_EXT_debug_utils\0").expect("Wrong extension string")
} }
pub unsafe fn debug_utils_set_object_name_ext( pub unsafe fn debug_utils_set_object_name(
&self, &self,
device: vk::Device, device: vk::Device,
name_info: &vk::DebugUtilsObjectNameInfoEXT, name_info: &vk::DebugUtilsObjectNameInfoEXT,
) -> VkResult<()> { ) -> VkResult<()> {
let err_code = self.debug_utils_fn.set_debug_utils_object_name_ext(device, name_info); let err_code = self
.debug_utils_fn
.set_debug_utils_object_name_ext(device, name_info);
match err_code { match err_code {
vk::Result::SUCCESS => Ok(()), vk::Result::SUCCESS => Ok(()),
_ => Err(err_code), _ => Err(err_code),
} }
} }
pub unsafe fn debug_utils_set_object_tag_ext( pub unsafe fn debug_utils_set_object_tag(
&self, &self,
device: vk::Device, device: vk::Device,
tag_info: &vk::DebugUtilsObjectTagInfoEXT, tag_info: &vk::DebugUtilsObjectTagInfoEXT,
) -> VkResult<()> { ) -> VkResult<()> {
let err_code = self.debug_utils_fn.set_debug_utils_object_tag_ext(device, tag_info); let err_code = self
.debug_utils_fn
.set_debug_utils_object_tag_ext(device, tag_info);
match err_code { match err_code {
vk::Result::SUCCESS => Ok(()), vk::Result::SUCCESS => Ok(()),
_ => Err(err_code), _ => Err(err_code),
} }
} }
pub unsafe fn cmd_begin_debug_utils_label_ext( pub unsafe fn cmd_begin_debug_utils_label(
&self, &self,
command_buffer: vk::CommandBuffer, command_buffer: vk::CommandBuffer,
label: &vk::DebugUtilsLabelEXT, label: &vk::DebugUtilsLabelEXT,
@ -62,12 +63,12 @@ impl DebugUtils {
.cmd_begin_debug_utils_label_ext(command_buffer, label); .cmd_begin_debug_utils_label_ext(command_buffer, label);
} }
pub unsafe fn cmd_end_debug_utils_label_ext(&self, command_buffer: vk::CommandBuffer) { pub unsafe fn cmd_end_debug_utils_label(&self, command_buffer: vk::CommandBuffer) {
self.debug_utils_fn self.debug_utils_fn
.cmd_end_debug_utils_label_ext(command_buffer); .cmd_end_debug_utils_label_ext(command_buffer);
} }
pub unsafe fn cmd_insert_debug_utils_label_ext( pub unsafe fn cmd_insert_debug_utils_label(
&self, &self,
command_buffer: vk::CommandBuffer, command_buffer: vk::CommandBuffer,
label: &vk::DebugUtilsLabelEXT, label: &vk::DebugUtilsLabelEXT,
@ -76,7 +77,7 @@ impl DebugUtils {
.cmd_insert_debug_utils_label_ext(command_buffer, label); .cmd_insert_debug_utils_label_ext(command_buffer, label);
} }
pub unsafe fn queue_begin_debug_utils_label_ext( pub unsafe fn queue_begin_debug_utils_label(
&self, &self,
queue: vk::Queue, queue: vk::Queue,
label: &vk::DebugUtilsLabelEXT, label: &vk::DebugUtilsLabelEXT,
@ -85,11 +86,11 @@ impl DebugUtils {
.queue_begin_debug_utils_label_ext(queue, label); .queue_begin_debug_utils_label_ext(queue, label);
} }
pub unsafe fn queue_end_debug_utils_label_ext(&self, queue: vk::Queue) { pub unsafe fn queue_end_debug_utils_label(&self, queue: vk::Queue) {
self.debug_utils_fn.queue_end_debug_utils_label_ext(queue); self.debug_utils_fn.queue_end_debug_utils_label_ext(queue);
} }
pub unsafe fn queue_insert_debug_utils_label_ext( pub unsafe fn queue_insert_debug_utils_label(
&self, &self,
queue: vk::Queue, queue: vk::Queue,
label: &vk::DebugUtilsLabelEXT, label: &vk::DebugUtilsLabelEXT,
@ -98,7 +99,7 @@ impl DebugUtils {
.queue_insert_debug_utils_label_ext(queue, label); .queue_insert_debug_utils_label_ext(queue, label);
} }
pub unsafe fn create_debug_utils_messenger_ext( pub unsafe fn create_debug_utils_messenger(
&self, &self,
create_info: &vk::DebugUtilsMessengerCreateInfoEXT, create_info: &vk::DebugUtilsMessengerCreateInfoEXT,
allocator: Option<&vk::AllocationCallbacks>, allocator: Option<&vk::AllocationCallbacks>,
@ -116,7 +117,7 @@ impl DebugUtils {
} }
} }
pub unsafe fn destroy_debug_utils_messenger_ext( pub unsafe fn destroy_debug_utils_messenger(
&self, &self,
messenger: vk::DebugUtilsMessengerEXT, messenger: vk::DebugUtilsMessengerEXT,
allocator: Option<&vk::AllocationCallbacks>, allocator: Option<&vk::AllocationCallbacks>,
@ -128,7 +129,7 @@ impl DebugUtils {
); );
} }
pub unsafe fn submit_debug_utils_message_ext( pub unsafe fn submit_debug_utils_message(
&self, &self,
instance: vk::Instance, instance: vk::Instance,
message_severity: vk::DebugUtilsMessageSeverityFlagsEXT, message_severity: vk::DebugUtilsMessageSeverityFlagsEXT,

View file

@ -0,0 +1,7 @@
pub use self::debug_marker::DebugMarker;
pub use self::debug_report::DebugReport;
pub use self::debug_utils::DebugUtils;
mod debug_marker;
mod debug_report;
mod debug_utils;

View file

@ -13,10 +13,7 @@ pub struct AndroidSurface {
} }
impl AndroidSurface { impl AndroidSurface {
pub fn new<E: EntryV1_0, I: InstanceV1_0>( pub fn new<E: EntryV1_0, I: InstanceV1_0>(entry: &E, instance: &I) -> AndroidSurface {
entry: &E,
instance: &I,
) -> AndroidSurface {
let surface_fn = vk::KhrAndroidSurfaceFn::load(|name| unsafe { let surface_fn = vk::KhrAndroidSurfaceFn::load(|name| unsafe {
mem::transmute(entry.get_instance_proc_addr(instance.handle(), name.as_ptr())) mem::transmute(entry.get_instance_proc_addr(instance.handle(), name.as_ptr()))
}); });
@ -30,7 +27,7 @@ impl AndroidSurface {
CStr::from_bytes_with_nul(b"VK_KHR_android_surface\0").expect("Wrong extension string") CStr::from_bytes_with_nul(b"VK_KHR_android_surface\0").expect("Wrong extension string")
} }
pub unsafe fn create_android_surface_khr( pub unsafe fn create_android_surface(
&self, &self,
create_info: &vk::AndroidSurfaceCreateInfoKHR, create_info: &vk::AndroidSurfaceCreateInfoKHR,
allocation_callbacks: Option<&vk::AllocationCallbacks>, allocation_callbacks: Option<&vk::AllocationCallbacks>,

View file

@ -13,10 +13,7 @@ pub struct DisplaySwapchain {
} }
impl DisplaySwapchain { impl DisplaySwapchain {
pub fn new<I: InstanceV1_0, D: DeviceV1_0>( pub fn new<I: InstanceV1_0, D: DeviceV1_0>(instance: &I, device: &D) -> DisplaySwapchain {
instance: &I,
device: &D,
) -> DisplaySwapchain {
let swapchain_fn = vk::KhrDisplaySwapchainFn::load(|name| unsafe { let swapchain_fn = vk::KhrDisplaySwapchainFn::load(|name| unsafe {
mem::transmute(instance.get_device_proc_addr(device.handle(), name.as_ptr())) mem::transmute(instance.get_device_proc_addr(device.handle(), name.as_ptr()))
}); });
@ -30,7 +27,7 @@ impl DisplaySwapchain {
CStr::from_bytes_with_nul(b"VK_KHR_display_swapchain\0").expect("Wrong extension string") CStr::from_bytes_with_nul(b"VK_KHR_display_swapchain\0").expect("Wrong extension string")
} }
pub unsafe fn create_shared_swapchains_khr( pub unsafe fn create_shared_swapchains(
&self, &self,
create_infos: &[vk::SwapchainCreateInfoKHR], create_infos: &[vk::SwapchainCreateInfoKHR],
allocation_callbacks: Option<&vk::AllocationCallbacks>, allocation_callbacks: Option<&vk::AllocationCallbacks>,

View file

@ -0,0 +1,17 @@
pub use self::android_surface::AndroidSurface;
pub use self::display_swapchain::DisplaySwapchain;
pub use self::surface::Surface;
pub use self::swapchain::Swapchain;
pub use self::wayland_surface::WaylandSurface;
pub use self::win32_surface::Win32Surface;
pub use self::xcb_surface::XcbSurface;
pub use self::xlib_surface::XlibSurface;
mod android_surface;
mod display_swapchain;
mod surface;
mod swapchain;
mod wayland_surface;
mod win32_surface;
mod xcb_surface;
mod xlib_surface;

View file

@ -14,10 +14,7 @@ pub struct Surface {
} }
impl Surface { impl Surface {
pub fn new<E: EntryV1_0, I: InstanceV1_0>( pub fn new<E: EntryV1_0, I: InstanceV1_0>(entry: &E, instance: &I) -> Surface {
entry: &E,
instance: &I,
) -> Surface {
let surface_fn = vk::KhrSurfaceFn::load(|name| unsafe { let surface_fn = vk::KhrSurfaceFn::load(|name| unsafe {
mem::transmute(entry.get_instance_proc_addr(instance.handle(), name.as_ptr())) mem::transmute(entry.get_instance_proc_addr(instance.handle(), name.as_ptr()))
}); });
@ -31,7 +28,7 @@ impl Surface {
CStr::from_bytes_with_nul(b"VK_KHR_surface\0").expect("Wrong extension string") CStr::from_bytes_with_nul(b"VK_KHR_surface\0").expect("Wrong extension string")
} }
pub unsafe fn get_physical_device_surface_support_khr( pub unsafe fn get_physical_device_surface_support(
&self, &self,
physical_device: vk::PhysicalDevice, physical_device: vk::PhysicalDevice,
queue_index: u32, queue_index: u32,
@ -47,7 +44,7 @@ impl Surface {
b > 0 b > 0
} }
pub unsafe fn get_physical_device_surface_present_modes_khr( pub unsafe fn get_physical_device_surface_present_modes(
&self, &self,
physical_device: vk::PhysicalDevice, physical_device: vk::PhysicalDevice,
surface: vk::SurfaceKHR, surface: vk::SurfaceKHR,
@ -76,7 +73,7 @@ impl Surface {
} }
} }
pub unsafe fn get_physical_device_surface_capabilities_khr( pub unsafe fn get_physical_device_surface_capabilities(
&self, &self,
physical_device: vk::PhysicalDevice, physical_device: vk::PhysicalDevice,
surface: vk::SurfaceKHR, surface: vk::SurfaceKHR,
@ -95,7 +92,7 @@ impl Surface {
} }
} }
pub unsafe fn get_physical_device_surface_formats_khr( pub unsafe fn get_physical_device_surface_formats(
&self, &self,
physical_device: vk::PhysicalDevice, physical_device: vk::PhysicalDevice,
surface: vk::SurfaceKHR, surface: vk::SurfaceKHR,
@ -121,7 +118,7 @@ impl Surface {
} }
} }
pub unsafe fn destroy_surface_khr( pub unsafe fn destroy_surface(
&self, &self,
surface: vk::SurfaceKHR, surface: vk::SurfaceKHR,
allocation_callbacks: Option<&vk::AllocationCallbacks>, allocation_callbacks: Option<&vk::AllocationCallbacks>,

View file

@ -14,10 +14,7 @@ pub struct Swapchain {
} }
impl Swapchain { impl Swapchain {
pub fn new<I: InstanceV1_0, D: DeviceV1_0>( pub fn new<I: InstanceV1_0, D: DeviceV1_0>(instance: &I, device: &D) -> Swapchain {
instance: &I,
device: &D,
) -> Swapchain {
let swapchain_fn = vk::KhrSwapchainFn::load(|name| unsafe { let swapchain_fn = vk::KhrSwapchainFn::load(|name| unsafe {
mem::transmute(instance.get_device_proc_addr(device.handle(), name.as_ptr())) mem::transmute(instance.get_device_proc_addr(device.handle(), name.as_ptr()))
}); });
@ -31,7 +28,7 @@ impl Swapchain {
CStr::from_bytes_with_nul(b"VK_KHR_swapchain\0").expect("Wrong extension string") CStr::from_bytes_with_nul(b"VK_KHR_swapchain\0").expect("Wrong extension string")
} }
pub unsafe fn destroy_swapchain_khr( pub unsafe fn destroy_swapchain(
&self, &self,
swapchain: vk::SwapchainKHR, swapchain: vk::SwapchainKHR,
allocation_callbacks: Option<&vk::AllocationCallbacks>, allocation_callbacks: Option<&vk::AllocationCallbacks>,
@ -44,7 +41,7 @@ impl Swapchain {
} }
/// On success, returns the next image's index and whether the swapchain is suboptimal for the surface. /// On success, returns the next image's index and whether the swapchain is suboptimal for the surface.
pub unsafe fn acquire_next_image_khr( pub unsafe fn acquire_next_image(
&self, &self,
swapchain: vk::SwapchainKHR, swapchain: vk::SwapchainKHR,
timeout: u64, timeout: u64,
@ -67,7 +64,7 @@ impl Swapchain {
} }
} }
pub unsafe fn create_swapchain_khr( pub unsafe fn create_swapchain(
&self, &self,
create_info: &vk::SwapchainCreateInfoKHR, create_info: &vk::SwapchainCreateInfoKHR,
allocation_callbacks: Option<&vk::AllocationCallbacks>, allocation_callbacks: Option<&vk::AllocationCallbacks>,
@ -86,7 +83,7 @@ impl Swapchain {
} }
/// On success, returns whether the swapchain is suboptimal for the surface. /// On success, returns whether the swapchain is suboptimal for the surface.
pub unsafe fn queue_present_khr( pub unsafe fn queue_present(
&self, &self,
queue: vk::Queue, queue: vk::Queue,
create_info: &vk::PresentInfoKHR, create_info: &vk::PresentInfoKHR,
@ -99,7 +96,7 @@ impl Swapchain {
} }
} }
pub unsafe fn get_swapchain_images_khr( pub unsafe fn get_swapchain_images(
&self, &self,
swapchain: vk::SwapchainKHR, swapchain: vk::SwapchainKHR,
) -> VkResult<Vec<vk::Image>> { ) -> VkResult<Vec<vk::Image>> {

View file

@ -13,10 +13,7 @@ pub struct WaylandSurface {
} }
impl WaylandSurface { impl WaylandSurface {
pub fn new<E: EntryV1_0, I: InstanceV1_0>( pub fn new<E: EntryV1_0, I: InstanceV1_0>(entry: &E, instance: &I) -> WaylandSurface {
entry: &E,
instance: &I,
) -> WaylandSurface {
let surface_fn = vk::KhrWaylandSurfaceFn::load(|name| unsafe { let surface_fn = vk::KhrWaylandSurfaceFn::load(|name| unsafe {
mem::transmute(entry.get_instance_proc_addr(instance.handle(), name.as_ptr())) mem::transmute(entry.get_instance_proc_addr(instance.handle(), name.as_ptr()))
}); });
@ -30,7 +27,7 @@ impl WaylandSurface {
CStr::from_bytes_with_nul(b"VK_KHR_wayland_surface\0").expect("Wrong extension string") CStr::from_bytes_with_nul(b"VK_KHR_wayland_surface\0").expect("Wrong extension string")
} }
pub unsafe fn create_wayland_surface_khr( pub unsafe fn create_wayland_surface(
&self, &self,
create_info: &vk::WaylandSurfaceCreateInfoKHR, create_info: &vk::WaylandSurfaceCreateInfoKHR,
allocation_callbacks: Option<&vk::AllocationCallbacks>, allocation_callbacks: Option<&vk::AllocationCallbacks>,

View file

@ -13,10 +13,7 @@ pub struct Win32Surface {
} }
impl Win32Surface { impl Win32Surface {
pub fn new<E: EntryV1_0, I: InstanceV1_0>( pub fn new<E: EntryV1_0, I: InstanceV1_0>(entry: &E, instance: &I) -> Win32Surface {
entry: &E,
instance: &I,
) -> Win32Surface {
let surface_fn = vk::KhrWin32SurfaceFn::load(|name| unsafe { let surface_fn = vk::KhrWin32SurfaceFn::load(|name| unsafe {
mem::transmute(entry.get_instance_proc_addr(instance.handle(), name.as_ptr())) mem::transmute(entry.get_instance_proc_addr(instance.handle(), name.as_ptr()))
}); });
@ -30,7 +27,7 @@ impl Win32Surface {
CStr::from_bytes_with_nul(b"VK_KHR_win32_surface\0").expect("Wrong extension string") CStr::from_bytes_with_nul(b"VK_KHR_win32_surface\0").expect("Wrong extension string")
} }
pub unsafe fn create_win32_surface_khr( pub unsafe fn create_win32_surface(
&self, &self,
create_info: &vk::Win32SurfaceCreateInfoKHR, create_info: &vk::Win32SurfaceCreateInfoKHR,
allocation_callbacks: Option<&vk::AllocationCallbacks>, allocation_callbacks: Option<&vk::AllocationCallbacks>,

View file

@ -13,10 +13,7 @@ pub struct XcbSurface {
} }
impl XcbSurface { impl XcbSurface {
pub fn new<E: EntryV1_0, I: InstanceV1_0>( pub fn new<E: EntryV1_0, I: InstanceV1_0>(entry: &E, instance: &I) -> XcbSurface {
entry: &E,
instance: &I,
) -> XcbSurface {
let surface_fn = vk::KhrXcbSurfaceFn::load(|name| unsafe { let surface_fn = vk::KhrXcbSurfaceFn::load(|name| unsafe {
mem::transmute(entry.get_instance_proc_addr(instance.handle(), name.as_ptr())) mem::transmute(entry.get_instance_proc_addr(instance.handle(), name.as_ptr()))
}); });
@ -30,7 +27,7 @@ impl XcbSurface {
CStr::from_bytes_with_nul(b"VK_KHR_xcb_surface\0").expect("Wrong extension string") CStr::from_bytes_with_nul(b"VK_KHR_xcb_surface\0").expect("Wrong extension string")
} }
pub unsafe fn create_xcb_surface_khr( pub unsafe fn create_xcb_surface(
&self, &self,
create_info: &vk::XcbSurfaceCreateInfoKHR, create_info: &vk::XcbSurfaceCreateInfoKHR,
allocation_callbacks: Option<&vk::AllocationCallbacks>, allocation_callbacks: Option<&vk::AllocationCallbacks>,

View file

@ -13,10 +13,7 @@ pub struct XlibSurface {
} }
impl XlibSurface { impl XlibSurface {
pub fn new<E: EntryV1_0, I: InstanceV1_0>( pub fn new<E: EntryV1_0, I: InstanceV1_0>(entry: &E, instance: &I) -> XlibSurface {
entry: &E,
instance: &I,
) -> XlibSurface {
let surface_fn = vk::KhrXlibSurfaceFn::load(|name| unsafe { let surface_fn = vk::KhrXlibSurfaceFn::load(|name| unsafe {
mem::transmute(entry.get_instance_proc_addr(instance.handle(), name.as_ptr())) mem::transmute(entry.get_instance_proc_addr(instance.handle(), name.as_ptr()))
}); });
@ -30,7 +27,7 @@ impl XlibSurface {
CStr::from_bytes_with_nul(b"VK_KHR_xlib_surface\0").expect("Wrong extension string") CStr::from_bytes_with_nul(b"VK_KHR_xlib_surface\0").expect("Wrong extension string")
} }
pub unsafe fn create_xlib_surface_khr( pub unsafe fn create_xlib_surface(
&self, &self,
create_info: &vk::XlibSurfaceCreateInfoKHR, create_info: &vk::XlibSurfaceCreateInfoKHR,
allocation_callbacks: Option<&vk::AllocationCallbacks>, allocation_callbacks: Option<&vk::AllocationCallbacks>,

View file

@ -1,27 +1,4 @@
pub use self::android_surface::AndroidSurface; pub mod ext;
pub use self::debug_marker::DebugMarker; pub mod khr;
pub use self::debug_report::DebugReport; pub mod mvk;
pub use self::debug_utils::DebugUtils; pub mod nv;
pub use self::display_swapchain::DisplaySwapchain;
pub use self::ios_surface::IOSSurface;
pub use self::macos_surface::MacOSSurface;
pub use self::surface::Surface;
pub use self::swapchain::Swapchain;
pub use self::wayland_surface::WaylandSurface;
pub use self::win32_surface::Win32Surface;
pub use self::xcb_surface::XcbSurface;
pub use self::xlib_surface::XlibSurface;
mod android_surface;
mod debug_marker;
mod debug_report;
mod debug_utils;
mod display_swapchain;
mod ios_surface;
mod macos_surface;
mod surface;
mod swapchain;
mod wayland_surface;
mod win32_surface;
mod xcb_surface;
mod xlib_surface;

View file

@ -13,10 +13,7 @@ pub struct IOSSurface {
} }
impl IOSSurface { impl IOSSurface {
pub fn new<E: EntryV1_0, I: InstanceV1_0>( pub fn new<E: EntryV1_0, I: InstanceV1_0>(entry: &E, instance: &I) -> IOSSurface {
entry: &E,
instance: &I,
) -> IOSSurface{
let surface_fn = vk::MvkIosSurfaceFn::load(|name| unsafe { let surface_fn = vk::MvkIosSurfaceFn::load(|name| unsafe {
mem::transmute(entry.get_instance_proc_addr(instance.handle(), name.as_ptr())) mem::transmute(entry.get_instance_proc_addr(instance.handle(), name.as_ptr()))
}); });

View file

@ -13,10 +13,7 @@ pub struct MacOSSurface {
} }
impl MacOSSurface { impl MacOSSurface {
pub fn new<E: EntryV1_0, I: InstanceV1_0>( pub fn new<E: EntryV1_0, I: InstanceV1_0>(entry: &E, instance: &I) -> MacOSSurface {
entry: &E,
instance: &I,
) -> MacOSSurface {
let surface_fn = vk::MvkMacosSurfaceFn::load(|name| unsafe { let surface_fn = vk::MvkMacosSurfaceFn::load(|name| unsafe {
mem::transmute(entry.get_instance_proc_addr(instance.handle(), name.as_ptr())) mem::transmute(entry.get_instance_proc_addr(instance.handle(), name.as_ptr()))
}); });

View file

@ -0,0 +1,5 @@
pub use self::ios_surface::IOSSurface;
pub use self::macos_surface::MacOSSurface;
mod ios_surface;
mod macos_surface;

View file

@ -0,0 +1,67 @@
#![allow(dead_code)]
use std::ffi::CStr;
use std::mem;
use version::{DeviceV1_0, InstanceV1_0};
use vk;
#[derive(Clone)]
pub struct MeshShader {
mesh_shader_fn: vk::NvMeshShaderFn,
}
impl MeshShader {
pub fn new<I: InstanceV1_0, D: DeviceV1_0>(instance: &I, device: &D) -> MeshShader {
let mesh_shader_fn = vk::NvMeshShaderFn::load(|name| unsafe {
mem::transmute(instance.get_device_proc_addr(device.handle(), name.as_ptr()))
});
MeshShader { mesh_shader_fn }
}
pub unsafe fn cmd_draw_mesh_tasks(
&self,
command_buffer: vk::CommandBuffer,
task_count: u32,
first_task: u32,
) {
self.mesh_shader_fn
.cmd_draw_mesh_tasks_nv(command_buffer, task_count, first_task);
}
pub unsafe fn cmd_draw_mesh_tasks_indirect(
&self,
command_buffer: vk::CommandBuffer,
buffer: vk::Buffer,
offset: vk::DeviceSize,
draw_count: u32,
stride: u32,
) {
self.mesh_shader_fn.cmd_draw_mesh_tasks_indirect_nv(
command_buffer,
buffer,
offset,
draw_count,
stride,
);
}
pub unsafe fn cmd_draw_mesh_tasks_indirect_count(
&self,
command_buffer: vk::CommandBuffer,
buffer: vk::Buffer,
offset: vk::DeviceSize,
count_buffer: vk::Buffer,
count_buffer_offset: vk::DeviceSize,
max_draw_count: u32,
stride: u32,
) {
self.mesh_shader_fn.cmd_draw_mesh_tasks_indirect_count_nv(
command_buffer,
buffer,
offset,
count_buffer,
count_buffer_offset,
max_draw_count,
stride,
);
}
pub fn name() -> &'static CStr {
CStr::from_bytes_with_nul(b"VK_NV_mesh_shader\0").expect("Wrong extension string")
}
}

View file

@ -0,0 +1,3 @@
pub use self::mesh_shader::MeshShader;
mod mesh_shader;

View file

@ -1,6 +1,7 @@
#[macro_use] #[macro_use]
extern crate lazy_static; extern crate lazy_static;
extern crate shared_library; extern crate shared_library;
pub use device::Device; pub use device::Device;
pub use entry::{Entry, InstanceError, LoadingError}; pub use entry::{Entry, InstanceError, LoadingError};
pub use instance::Instance; pub use instance::Instance;

View file

@ -2,6 +2,7 @@ use std::iter::Iterator;
use std::marker::PhantomData; use std::marker::PhantomData;
use std::mem::size_of; use std::mem::size_of;
use std::os::raw::c_void; use std::os::raw::c_void;
use std::{io, slice};
use vk; use vk;
/// `Align` handles dynamic alignment. The is useful for dynamic uniform buffers where /// `Align` handles dynamic alignment. The is useful for dynamic uniform buffers where
@ -46,11 +47,7 @@ fn calc_padding(adr: vk::DeviceSize, align: vk::DeviceSize) -> vk::DeviceSize {
} }
impl<T> Align<T> { impl<T> Align<T> {
pub unsafe fn new( pub unsafe fn new(ptr: *mut c_void, alignment: vk::DeviceSize, size: vk::DeviceSize) -> Self {
ptr: *mut c_void,
alignment: vk::DeviceSize,
size: vk::DeviceSize,
) -> Self {
let padding = calc_padding(size_of::<T>() as vk::DeviceSize, alignment); let padding = calc_padding(size_of::<T>() as vk::DeviceSize, alignment);
let elem_size = size_of::<T>() as vk::DeviceSize + padding; let elem_size = size_of::<T>() as vk::DeviceSize + padding;
assert!(calc_padding(size, alignment) == 0, "size must be aligned"); assert!(calc_padding(size, alignment) == 0, "size must be aligned");
@ -84,3 +81,58 @@ impl<'a, T: Copy + 'a> Iterator for AlignIter<'a, T> {
} }
} }
} }
/// Decode SPIR-V from bytes.
///
/// This function handles SPIR-V of arbitrary endianness gracefully, and returns correctly aligned
/// storage.
///
/// # Examples
/// ```no_run
/// // Decode SPIR-V from a file
/// let mut file = std::fs::File::open("/path/to/shader.spv").unwrap();
/// let words = ash::util::read_spv(&mut file).unwrap();
/// ```
/// ```
/// // Decode SPIR-V from memory
/// const SPIRV: &[u8] = &[
/// // ...
/// # 0x03, 0x02, 0x23, 0x07,
/// ];
/// let words = ash::util::read_spv(&mut std::io::Cursor::new(&SPIRV[..])).unwrap();
/// ```
pub fn read_spv<R: io::Read + io::Seek>(x: &mut R) -> io::Result<Vec<u32>> {
let size = x.seek(io::SeekFrom::End(0))?;
if size % 4 != 0 {
return Err(io::Error::new(
io::ErrorKind::InvalidData,
"input length not divisible by 4",
));
}
if size > usize::max_value() as u64 {
return Err(io::Error::new(io::ErrorKind::InvalidData, "input too long"));
}
let words = (size / 4) as usize;
let mut result = Vec::<u32>::with_capacity(words);
x.seek(io::SeekFrom::Start(0))?;
unsafe {
x.read_exact(slice::from_raw_parts_mut(
result.as_mut_ptr() as *mut u8,
words * 4,
))?;
result.set_len(words);
}
const MAGIC_NUMBER: u32 = 0x07230203;
if result.len() > 0 && result[0] == MAGIC_NUMBER.swap_bytes() {
for word in &mut result {
*word = word.swap_bytes();
}
}
if result.len() == 0 || result[0] != MAGIC_NUMBER {
return Err(io::Error::new(
io::ErrorKind::InvalidData,
"input missing SPIR-V magic number",
));
}
Ok(result)
}

File diff suppressed because it is too large Load diff

View file

@ -3,7 +3,11 @@ use ash::vk;
#[test] #[test]
fn display_flags() { fn display_flags() {
assert_eq!((vk::AccessFlags::INDIRECT_COMMAND_READ | vk::AccessFlags::VERTEX_ATTRIBUTE_READ).to_string(), "INDIRECT_COMMAND_READ | VERTEX_ATTRIBUTE_READ"); assert_eq!(
(vk::AccessFlags::INDIRECT_COMMAND_READ | vk::AccessFlags::VERTEX_ATTRIBUTE_READ)
.to_string(),
"INDIRECT_COMMAND_READ | VERTEX_ATTRIBUTE_READ"
);
} }
#[test] #[test]

6
bors.toml Normal file
View file

@ -0,0 +1,6 @@
status = [
"continuous-integration/travis-ci/push",
"continuous-integration/appveyor/branch"
]
timeout_sec = 18000 # 5 hours

View file

@ -5,11 +5,9 @@ extern crate image;
use std::default::Default; use std::default::Default;
use std::ffi::CString; use std::ffi::CString;
use std::fs::File; use std::fs::File;
use std::io::Read;
use std::mem::{self, align_of}; use std::mem::{self, align_of};
use std::os::raw::c_void; use std::os::raw::c_void;
use std::path::Path; use std::path::Path;
use std::ptr;
use ash::util::*; use ash::util::*;
use ash::vk; use ash::vk;
@ -33,91 +31,70 @@ pub struct Vector3 {
fn main() { fn main() {
unsafe { unsafe {
let base = ExampleBase::new(1920, 1080); let base = ExampleBase::new(1920, 1080);
let renderpass_attachments = [ let renderpass_attachments = [
vk::AttachmentDescription { vk::AttachmentDescription {
format: base.surface_format.format, format: base.surface_format.format,
flags: vk::AttachmentDescriptionFlags::empty(),
samples: vk::SampleCountFlags::TYPE_1, samples: vk::SampleCountFlags::TYPE_1,
load_op: vk::AttachmentLoadOp::CLEAR, load_op: vk::AttachmentLoadOp::CLEAR,
store_op: vk::AttachmentStoreOp::STORE, store_op: vk::AttachmentStoreOp::STORE,
stencil_load_op: vk::AttachmentLoadOp::DONT_CARE,
stencil_store_op: vk::AttachmentStoreOp::DONT_CARE,
initial_layout: vk::ImageLayout::UNDEFINED,
final_layout: vk::ImageLayout::PRESENT_SRC_KHR, final_layout: vk::ImageLayout::PRESENT_SRC_KHR,
..Default::default()
}, },
vk::AttachmentDescription { vk::AttachmentDescription {
format: vk::Format::D16_UNORM, format: vk::Format::D16_UNORM,
flags: vk::AttachmentDescriptionFlags::empty(),
samples: vk::SampleCountFlags::TYPE_1, samples: vk::SampleCountFlags::TYPE_1,
load_op: vk::AttachmentLoadOp::CLEAR, load_op: vk::AttachmentLoadOp::CLEAR,
store_op: vk::AttachmentStoreOp::DONT_CARE,
stencil_load_op: vk::AttachmentLoadOp::DONT_CARE,
stencil_store_op: vk::AttachmentStoreOp::DONT_CARE,
initial_layout: vk::ImageLayout::DEPTH_STENCIL_ATTACHMENT_OPTIMAL, initial_layout: vk::ImageLayout::DEPTH_STENCIL_ATTACHMENT_OPTIMAL,
final_layout: vk::ImageLayout::DEPTH_STENCIL_ATTACHMENT_OPTIMAL, final_layout: vk::ImageLayout::DEPTH_STENCIL_ATTACHMENT_OPTIMAL,
..Default::default()
}, },
]; ];
let color_attachment_ref = vk::AttachmentReference { let color_attachment_refs = [vk::AttachmentReference {
attachment: 0, attachment: 0,
layout: vk::ImageLayout::COLOR_ATTACHMENT_OPTIMAL, layout: vk::ImageLayout::COLOR_ATTACHMENT_OPTIMAL,
}; }];
let depth_attachment_ref = vk::AttachmentReference { let depth_attachment_ref = vk::AttachmentReference {
attachment: 1, attachment: 1,
layout: vk::ImageLayout::DEPTH_STENCIL_ATTACHMENT_OPTIMAL, layout: vk::ImageLayout::DEPTH_STENCIL_ATTACHMENT_OPTIMAL,
}; };
let dependency = vk::SubpassDependency { let dependencies = [vk::SubpassDependency {
dependency_flags: Default::default(),
src_subpass: vk::SUBPASS_EXTERNAL, src_subpass: vk::SUBPASS_EXTERNAL,
dst_subpass: Default::default(),
src_stage_mask: vk::PipelineStageFlags::COLOR_ATTACHMENT_OUTPUT, src_stage_mask: vk::PipelineStageFlags::COLOR_ATTACHMENT_OUTPUT,
src_access_mask: Default::default(),
dst_access_mask: vk::AccessFlags::COLOR_ATTACHMENT_READ dst_access_mask: vk::AccessFlags::COLOR_ATTACHMENT_READ
| vk::AccessFlags::COLOR_ATTACHMENT_WRITE, | vk::AccessFlags::COLOR_ATTACHMENT_WRITE,
dst_stage_mask: vk::PipelineStageFlags::COLOR_ATTACHMENT_OUTPUT, dst_stage_mask: vk::PipelineStageFlags::COLOR_ATTACHMENT_OUTPUT,
}; ..Default::default()
let subpass = vk::SubpassDescription { }];
color_attachment_count: 1,
p_color_attachments: &color_attachment_ref, let subpasses = [vk::SubpassDescription::builder()
p_depth_stencil_attachment: &depth_attachment_ref, .color_attachments(&color_attachment_refs)
flags: Default::default(), .depth_stencil_attachment(&depth_attachment_ref)
pipeline_bind_point: vk::PipelineBindPoint::GRAPHICS, .pipeline_bind_point(vk::PipelineBindPoint::GRAPHICS)
input_attachment_count: 0, .build()];
p_input_attachments: ptr::null(),
p_resolve_attachments: ptr::null(), let renderpass_create_info = vk::RenderPassCreateInfo::builder()
preserve_attachment_count: 0, .attachments(&renderpass_attachments)
p_preserve_attachments: ptr::null(), .subpasses(&subpasses)
}; .dependencies(&dependencies);
let renderpass_create_info = vk::RenderPassCreateInfo {
s_type: vk::StructureType::RENDER_PASS_CREATE_INFO,
flags: Default::default(),
p_next: ptr::null(),
attachment_count: renderpass_attachments.len() as u32,
p_attachments: renderpass_attachments.as_ptr(),
subpass_count: 1,
p_subpasses: &subpass,
dependency_count: 1,
p_dependencies: &dependency,
};
let renderpass = base let renderpass = base
.device .device
.create_render_pass(&renderpass_create_info, None) .create_render_pass(&renderpass_create_info, None)
.unwrap(); .unwrap();
let framebuffers: Vec<vk::Framebuffer> = base let framebuffers: Vec<vk::Framebuffer> = base
.present_image_views .present_image_views
.iter() .iter()
.map(|&present_image_view| { .map(|&present_image_view| {
let framebuffer_attachments = [present_image_view, base.depth_image_view]; let framebuffer_attachments = [present_image_view, base.depth_image_view];
let frame_buffer_create_info = vk::FramebufferCreateInfo { let frame_buffer_create_info = vk::FramebufferCreateInfo::builder()
s_type: vk::StructureType::FRAMEBUFFER_CREATE_INFO, .render_pass(renderpass)
p_next: ptr::null(), .attachments(&framebuffer_attachments)
flags: Default::default(), .width(base.surface_resolution.width)
render_pass: renderpass, .height(base.surface_resolution.height)
attachment_count: framebuffer_attachments.len() as u32, .layers(1);
p_attachments: framebuffer_attachments.as_ptr(),
width: base.surface_resolution.width,
height: base.surface_resolution.height,
layers: 1,
};
base.device base.device
.create_framebuffer(&frame_buffer_create_info, None) .create_framebuffer(&frame_buffer_create_info, None)
.unwrap() .unwrap()
@ -125,28 +102,23 @@ fn main() {
.collect(); .collect();
let index_buffer_data = [0u32, 1, 2, 2, 3, 0]; let index_buffer_data = [0u32, 1, 2, 2, 3, 0];
let index_buffer_info = vk::BufferCreateInfo { let index_buffer_info = vk::BufferCreateInfo {
s_type: vk::StructureType::BUFFER_CREATE_INFO,
p_next: ptr::null(),
flags: vk::BufferCreateFlags::empty(),
size: std::mem::size_of_val(&index_buffer_data) as u64, size: std::mem::size_of_val(&index_buffer_data) as u64,
usage: vk::BufferUsageFlags::INDEX_BUFFER, usage: vk::BufferUsageFlags::INDEX_BUFFER,
sharing_mode: vk::SharingMode::EXCLUSIVE, sharing_mode: vk::SharingMode::EXCLUSIVE,
queue_family_index_count: 0, ..Default::default()
p_queue_family_indices: ptr::null(),
}; };
let index_buffer = base.device.create_buffer(&index_buffer_info, None).unwrap(); let index_buffer = base.device.create_buffer(&index_buffer_info, None).unwrap();
let index_buffer_memory_req = base.device.get_buffer_memory_requirements(index_buffer); let index_buffer_memory_req = base.device.get_buffer_memory_requirements(index_buffer);
let index_buffer_memory_index = let index_buffer_memory_index = find_memorytype_index(
find_memorytype_index( &index_buffer_memory_req,
&index_buffer_memory_req, &base.device_memory_properties,
&base.device_memory_properties, vk::MemoryPropertyFlags::HOST_VISIBLE,
vk::MemoryPropertyFlags::HOST_VISIBLE, )
).expect("Unable to find suitable memorytype for the index buffer."); .expect("Unable to find suitable memorytype for the index buffer.");
let index_allocate_info = vk::MemoryAllocateInfo { let index_allocate_info = vk::MemoryAllocateInfo {
s_type: vk::StructureType::MEMORY_ALLOCATE_INFO,
p_next: ptr::null(),
allocation_size: index_buffer_memory_req.size, allocation_size: index_buffer_memory_req.size,
memory_type_index: index_buffer_memory_index, memory_type_index: index_buffer_memory_index,
..Default::default()
}; };
let index_buffer_memory = base let index_buffer_memory = base
.device .device
@ -191,14 +163,10 @@ fn main() {
}, },
]; ];
let vertex_input_buffer_info = vk::BufferCreateInfo { let vertex_input_buffer_info = vk::BufferCreateInfo {
s_type: vk::StructureType::BUFFER_CREATE_INFO,
p_next: ptr::null(),
flags: vk::BufferCreateFlags::empty(),
size: std::mem::size_of_val(&vertices) as u64, size: std::mem::size_of_val(&vertices) as u64,
usage: vk::BufferUsageFlags::VERTEX_BUFFER, usage: vk::BufferUsageFlags::VERTEX_BUFFER,
sharing_mode: vk::SharingMode::EXCLUSIVE, sharing_mode: vk::SharingMode::EXCLUSIVE,
queue_family_index_count: 0, ..Default::default()
p_queue_family_indices: ptr::null(),
}; };
let vertex_input_buffer = base let vertex_input_buffer = base
.device .device
@ -207,23 +175,23 @@ fn main() {
let vertex_input_buffer_memory_req = base let vertex_input_buffer_memory_req = base
.device .device
.get_buffer_memory_requirements(vertex_input_buffer); .get_buffer_memory_requirements(vertex_input_buffer);
let vertex_input_buffer_memory_index = let vertex_input_buffer_memory_index = find_memorytype_index(
find_memorytype_index( &vertex_input_buffer_memory_req,
&vertex_input_buffer_memory_req, &base.device_memory_properties,
&base.device_memory_properties, vk::MemoryPropertyFlags::HOST_VISIBLE,
vk::MemoryPropertyFlags::HOST_VISIBLE, )
).expect("Unable to find suitable memorytype for the vertex buffer."); .expect("Unable to find suitable memorytype for the vertex buffer.");
let vertex_buffer_allocate_info = vk::MemoryAllocateInfo { let vertex_buffer_allocate_info = vk::MemoryAllocateInfo {
s_type: vk::StructureType::MEMORY_ALLOCATE_INFO,
p_next: ptr::null(),
allocation_size: vertex_input_buffer_memory_req.size, allocation_size: vertex_input_buffer_memory_req.size,
memory_type_index: vertex_input_buffer_memory_index, memory_type_index: vertex_input_buffer_memory_index,
..Default::default()
}; };
let vertex_input_buffer_memory = base let vertex_input_buffer_memory = base
.device .device
.allocate_memory(&vertex_buffer_allocate_info, None) .allocate_memory(&vertex_buffer_allocate_info, None)
.unwrap(); .unwrap();
let vert_ptr = base let vert_ptr = base
.device .device
.map_memory( .map_memory(
@ -251,14 +219,10 @@ fn main() {
_pad: 0.0, _pad: 0.0,
}; };
let uniform_color_buffer_info = vk::BufferCreateInfo { let uniform_color_buffer_info = vk::BufferCreateInfo {
s_type: vk::StructureType::BUFFER_CREATE_INFO,
p_next: ptr::null(),
flags: vk::BufferCreateFlags::empty(),
size: std::mem::size_of_val(&uniform_color_buffer_data) as u64, size: std::mem::size_of_val(&uniform_color_buffer_data) as u64,
usage: vk::BufferUsageFlags::UNIFORM_BUFFER, usage: vk::BufferUsageFlags::UNIFORM_BUFFER,
sharing_mode: vk::SharingMode::EXCLUSIVE, sharing_mode: vk::SharingMode::EXCLUSIVE,
queue_family_index_count: 0, ..Default::default()
p_queue_family_indices: ptr::null(),
}; };
let uniform_color_buffer = base let uniform_color_buffer = base
.device .device
@ -267,18 +231,17 @@ fn main() {
let uniform_color_buffer_memory_req = base let uniform_color_buffer_memory_req = base
.device .device
.get_buffer_memory_requirements(uniform_color_buffer); .get_buffer_memory_requirements(uniform_color_buffer);
let uniform_color_buffer_memory_index = let uniform_color_buffer_memory_index = find_memorytype_index(
find_memorytype_index( &uniform_color_buffer_memory_req,
&uniform_color_buffer_memory_req, &base.device_memory_properties,
&base.device_memory_properties, vk::MemoryPropertyFlags::HOST_VISIBLE,
vk::MemoryPropertyFlags::HOST_VISIBLE, )
).expect("Unable to find suitable memorytype for the vertex buffer."); .expect("Unable to find suitable memorytype for the vertex buffer.");
let uniform_color_buffer_allocate_info = vk::MemoryAllocateInfo { let uniform_color_buffer_allocate_info = vk::MemoryAllocateInfo {
s_type: vk::StructureType::MEMORY_ALLOCATE_INFO,
p_next: ptr::null(),
allocation_size: uniform_color_buffer_memory_req.size, allocation_size: uniform_color_buffer_memory_req.size,
memory_type_index: uniform_color_buffer_memory_index, memory_type_index: uniform_color_buffer_memory_index,
..Default::default()
}; };
let uniform_color_buffer_memory = base let uniform_color_buffer_memory = base
.device .device
@ -308,29 +271,24 @@ fn main() {
let image_dimensions = image.dimensions(); let image_dimensions = image.dimensions();
let image_data = image.into_raw(); let image_data = image.into_raw();
let image_buffer_info = vk::BufferCreateInfo { let image_buffer_info = vk::BufferCreateInfo {
s_type: vk::StructureType::BUFFER_CREATE_INFO,
p_next: ptr::null(),
flags: vk::BufferCreateFlags::empty(),
size: (std::mem::size_of::<u8>() * image_data.len()) as u64, size: (std::mem::size_of::<u8>() * image_data.len()) as u64,
usage: vk::BufferUsageFlags::TRANSFER_SRC, usage: vk::BufferUsageFlags::TRANSFER_SRC,
sharing_mode: vk::SharingMode::EXCLUSIVE, sharing_mode: vk::SharingMode::EXCLUSIVE,
queue_family_index_count: 0, ..Default::default()
p_queue_family_indices: ptr::null(),
}; };
let image_buffer = base.device.create_buffer(&image_buffer_info, None).unwrap(); let image_buffer = base.device.create_buffer(&image_buffer_info, None).unwrap();
let image_buffer_memory_req = base.device.get_buffer_memory_requirements(image_buffer); let image_buffer_memory_req = base.device.get_buffer_memory_requirements(image_buffer);
let image_buffer_memory_index = let image_buffer_memory_index = find_memorytype_index(
find_memorytype_index( &image_buffer_memory_req,
&image_buffer_memory_req, &base.device_memory_properties,
&base.device_memory_properties, vk::MemoryPropertyFlags::HOST_VISIBLE,
vk::MemoryPropertyFlags::HOST_VISIBLE, )
).expect("Unable to find suitable memorytype for the vertex buffer."); .expect("Unable to find suitable memorytype for the vertex buffer.");
let image_buffer_allocate_info = vk::MemoryAllocateInfo { let image_buffer_allocate_info = vk::MemoryAllocateInfo {
s_type: vk::StructureType::MEMORY_ALLOCATE_INFO,
p_next: ptr::null(),
allocation_size: image_buffer_memory_req.size, allocation_size: image_buffer_memory_req.size,
memory_type_index: image_buffer_memory_index, memory_type_index: image_buffer_memory_index,
..Default::default()
}; };
let image_buffer_memory = base let image_buffer_memory = base
.device .device
@ -357,9 +315,6 @@ fn main() {
.unwrap(); .unwrap();
let texture_create_info = vk::ImageCreateInfo { let texture_create_info = vk::ImageCreateInfo {
s_type: vk::StructureType::IMAGE_CREATE_INFO,
p_next: ptr::null(),
flags: Default::default(),
image_type: vk::ImageType::TYPE_2D, image_type: vk::ImageType::TYPE_2D,
format: vk::Format::R8G8B8A8_UNORM, format: vk::Format::R8G8B8A8_UNORM,
extent: vk::Extent3D { extent: vk::Extent3D {
@ -373,27 +328,24 @@ fn main() {
tiling: vk::ImageTiling::OPTIMAL, tiling: vk::ImageTiling::OPTIMAL,
usage: vk::ImageUsageFlags::TRANSFER_DST | vk::ImageUsageFlags::SAMPLED, usage: vk::ImageUsageFlags::TRANSFER_DST | vk::ImageUsageFlags::SAMPLED,
sharing_mode: vk::SharingMode::EXCLUSIVE, sharing_mode: vk::SharingMode::EXCLUSIVE,
queue_family_index_count: 0, ..Default::default()
p_queue_family_indices: ptr::null(),
initial_layout: vk::ImageLayout::UNDEFINED,
}; };
let texture_image = base let texture_image = base
.device .device
.create_image(&texture_create_info, None) .create_image(&texture_create_info, None)
.unwrap(); .unwrap();
let texture_memory_req = base.device.get_image_memory_requirements(texture_image); let texture_memory_req = base.device.get_image_memory_requirements(texture_image);
let texture_memory_index = let texture_memory_index = find_memorytype_index(
find_memorytype_index( &texture_memory_req,
&texture_memory_req, &base.device_memory_properties,
&base.device_memory_properties, vk::MemoryPropertyFlags::DEVICE_LOCAL,
vk::MemoryPropertyFlags::DEVICE_LOCAL, )
).expect("Unable to find suitable memory index for depth image."); .expect("Unable to find suitable memory index for depth image.");
let texture_allocate_info = vk::MemoryAllocateInfo { let texture_allocate_info = vk::MemoryAllocateInfo {
s_type: vk::StructureType::MEMORY_ALLOCATE_INFO,
p_next: ptr::null(),
allocation_size: texture_memory_req.size, allocation_size: texture_memory_req.size,
memory_type_index: texture_memory_index, memory_type_index: texture_memory_index,
..Default::default()
}; };
let texture_memory = base let texture_memory = base
.device .device
@ -407,27 +359,21 @@ fn main() {
&base.device, &base.device,
base.setup_command_buffer, base.setup_command_buffer,
base.present_queue, base.present_queue,
&[vk::PipelineStageFlags::TOP_OF_PIPE], &[],
&[], &[],
&[], &[],
|device, texture_command_buffer| { |device, texture_command_buffer| {
let texture_barrier = vk::ImageMemoryBarrier { let texture_barrier = vk::ImageMemoryBarrier {
s_type: vk::StructureType::IMAGE_MEMORY_BARRIER,
p_next: ptr::null(),
src_access_mask: Default::default(),
dst_access_mask: vk::AccessFlags::TRANSFER_WRITE, dst_access_mask: vk::AccessFlags::TRANSFER_WRITE,
old_layout: vk::ImageLayout::UNDEFINED,
new_layout: vk::ImageLayout::TRANSFER_DST_OPTIMAL, new_layout: vk::ImageLayout::TRANSFER_DST_OPTIMAL,
src_queue_family_index: vk::QUEUE_FAMILY_IGNORED,
dst_queue_family_index: vk::QUEUE_FAMILY_IGNORED,
image: texture_image, image: texture_image,
subresource_range: vk::ImageSubresourceRange { subresource_range: vk::ImageSubresourceRange {
aspect_mask: vk::ImageAspectFlags::COLOR, aspect_mask: vk::ImageAspectFlags::COLOR,
base_mip_level: 0,
level_count: 1, level_count: 1,
base_array_layer: 0,
layer_count: 1, layer_count: 1,
..Default::default()
}, },
..Default::default()
}; };
device.cmd_pipeline_barrier( device.cmd_pipeline_barrier(
texture_command_buffer, texture_command_buffer,
@ -438,48 +384,39 @@ fn main() {
&[], &[],
&[texture_barrier], &[texture_barrier],
); );
let buffer_copy_regions = [vk::BufferImageCopy { let buffer_copy_regions = vk::BufferImageCopy::builder()
image_subresource: vk::ImageSubresourceLayers { .image_subresource(
aspect_mask: vk::ImageAspectFlags::COLOR, vk::ImageSubresourceLayers::builder()
mip_level: 0, .aspect_mask(vk::ImageAspectFlags::COLOR)
base_array_layer: 0, .layer_count(1)
layer_count: 1, .build(),
}, )
image_extent: vk::Extent3D { .image_extent(vk::Extent3D {
width: image_dimensions.0, width: image_dimensions.0,
height: image_dimensions.1, height: image_dimensions.1,
depth: 1, depth: 1,
}, });
buffer_offset: 0,
// FIX ME
buffer_image_height: 0,
buffer_row_length: 0,
image_offset: vk::Offset3D { x: 0, y: 0, z: 0 },
}];
device.cmd_copy_buffer_to_image( device.cmd_copy_buffer_to_image(
texture_command_buffer, texture_command_buffer,
image_buffer, image_buffer,
texture_image, texture_image,
vk::ImageLayout::TRANSFER_DST_OPTIMAL, vk::ImageLayout::TRANSFER_DST_OPTIMAL,
&buffer_copy_regions, &[buffer_copy_regions.build()],
); );
let texture_barrier_end = vk::ImageMemoryBarrier { let texture_barrier_end = vk::ImageMemoryBarrier {
s_type: vk::StructureType::IMAGE_MEMORY_BARRIER,
p_next: ptr::null(),
src_access_mask: vk::AccessFlags::TRANSFER_WRITE, src_access_mask: vk::AccessFlags::TRANSFER_WRITE,
dst_access_mask: vk::AccessFlags::SHADER_READ, dst_access_mask: vk::AccessFlags::SHADER_READ,
old_layout: vk::ImageLayout::TRANSFER_DST_OPTIMAL, old_layout: vk::ImageLayout::TRANSFER_DST_OPTIMAL,
new_layout: vk::ImageLayout::SHADER_READ_ONLY_OPTIMAL, new_layout: vk::ImageLayout::SHADER_READ_ONLY_OPTIMAL,
src_queue_family_index: vk::QUEUE_FAMILY_IGNORED,
dst_queue_family_index: vk::QUEUE_FAMILY_IGNORED,
image: texture_image, image: texture_image,
subresource_range: vk::ImageSubresourceRange { subresource_range: vk::ImageSubresourceRange {
aspect_mask: vk::ImageAspectFlags::COLOR, aspect_mask: vk::ImageAspectFlags::COLOR,
base_mip_level: 0,
level_count: 1, level_count: 1,
base_array_layer: 0,
layer_count: 1, layer_count: 1,
..Default::default()
}, },
..Default::default()
}; };
device.cmd_pipeline_barrier( device.cmd_pipeline_barrier(
texture_command_buffer, texture_command_buffer,
@ -494,32 +431,21 @@ fn main() {
); );
let sampler_info = vk::SamplerCreateInfo { let sampler_info = vk::SamplerCreateInfo {
s_type: vk::StructureType::SAMPLER_CREATE_INFO,
p_next: ptr::null(),
flags: Default::default(),
mag_filter: vk::Filter::LINEAR, mag_filter: vk::Filter::LINEAR,
min_filter: vk::Filter::LINEAR, min_filter: vk::Filter::LINEAR,
mipmap_mode: vk::SamplerMipmapMode::LINEAR, mipmap_mode: vk::SamplerMipmapMode::LINEAR,
address_mode_u: vk::SamplerAddressMode::MIRRORED_REPEAT, address_mode_u: vk::SamplerAddressMode::MIRRORED_REPEAT,
address_mode_v: vk::SamplerAddressMode::MIRRORED_REPEAT, address_mode_v: vk::SamplerAddressMode::MIRRORED_REPEAT,
address_mode_w: vk::SamplerAddressMode::MIRRORED_REPEAT, address_mode_w: vk::SamplerAddressMode::MIRRORED_REPEAT,
mip_lod_bias: 0.0,
min_lod: 0.0,
max_lod: 0.0,
anisotropy_enable: 0,
max_anisotropy: 1.0, max_anisotropy: 1.0,
border_color: vk::BorderColor::FLOAT_OPAQUE_WHITE, border_color: vk::BorderColor::FLOAT_OPAQUE_WHITE,
compare_enable: 0,
compare_op: vk::CompareOp::NEVER, compare_op: vk::CompareOp::NEVER,
unnormalized_coordinates: 0, ..Default::default()
}; };
let sampler = base.device.create_sampler(&sampler_info, None).unwrap(); let sampler = base.device.create_sampler(&sampler_info, None).unwrap();
let tex_image_view_info = vk::ImageViewCreateInfo { let tex_image_view_info = vk::ImageViewCreateInfo {
s_type: vk::StructureType::IMAGE_VIEW_CREATE_INFO,
p_next: ptr::null(),
flags: Default::default(),
view_type: vk::ImageViewType::TYPE_2D, view_type: vk::ImageViewType::TYPE_2D,
format: texture_create_info.format, format: texture_create_info.format,
components: vk::ComponentMapping { components: vk::ComponentMapping {
@ -530,12 +456,12 @@ fn main() {
}, },
subresource_range: vk::ImageSubresourceRange { subresource_range: vk::ImageSubresourceRange {
aspect_mask: vk::ImageAspectFlags::COLOR, aspect_mask: vk::ImageAspectFlags::COLOR,
base_mip_level: 0,
level_count: 1, level_count: 1,
base_array_layer: 0,
layer_count: 1, layer_count: 1,
..Default::default()
}, },
image: texture_image, image: texture_image,
..Default::default()
}; };
let tex_image_view = base let tex_image_view = base
.device .device
@ -551,53 +477,40 @@ fn main() {
descriptor_count: 1, descriptor_count: 1,
}, },
]; ];
let descriptor_pool_info = vk::DescriptorPoolCreateInfo { let descriptor_pool_info = vk::DescriptorPoolCreateInfo::builder()
s_type: vk::StructureType::DESCRIPTOR_POOL_CREATE_INFO, .pool_sizes(&descriptor_sizes)
p_next: ptr::null(), .max_sets(1);
flags: Default::default(),
pool_size_count: descriptor_sizes.len() as u32,
p_pool_sizes: descriptor_sizes.as_ptr(),
max_sets: 1,
};
let descriptor_pool = base let descriptor_pool = base
.device .device
.create_descriptor_pool(&descriptor_pool_info, None) .create_descriptor_pool(&descriptor_pool_info, None)
.unwrap(); .unwrap();
let desc_layout_bindings = [ let desc_layout_bindings = [
vk::DescriptorSetLayoutBinding { vk::DescriptorSetLayoutBinding {
binding: 0,
descriptor_type: vk::DescriptorType::UNIFORM_BUFFER, descriptor_type: vk::DescriptorType::UNIFORM_BUFFER,
descriptor_count: 1, descriptor_count: 1,
stage_flags: vk::ShaderStageFlags::FRAGMENT, stage_flags: vk::ShaderStageFlags::FRAGMENT,
p_immutable_samplers: ptr::null(), ..Default::default()
}, },
vk::DescriptorSetLayoutBinding { vk::DescriptorSetLayoutBinding {
binding: 1, binding: 1,
descriptor_type: vk::DescriptorType::COMBINED_IMAGE_SAMPLER, descriptor_type: vk::DescriptorType::COMBINED_IMAGE_SAMPLER,
descriptor_count: 1, descriptor_count: 1,
stage_flags: vk::ShaderStageFlags::FRAGMENT, stage_flags: vk::ShaderStageFlags::FRAGMENT,
p_immutable_samplers: ptr::null(), ..Default::default()
}, },
]; ];
let descriptor_info = vk::DescriptorSetLayoutCreateInfo { let descriptor_info =
s_type: vk::StructureType::DESCRIPTOR_SET_LAYOUT_CREATE_INFO, vk::DescriptorSetLayoutCreateInfo::builder().bindings(&desc_layout_bindings);
p_next: ptr::null(),
flags: Default::default(),
binding_count: desc_layout_bindings.len() as u32,
p_bindings: desc_layout_bindings.as_ptr(),
};
let desc_set_layouts = [base let desc_set_layouts = [base
.device .device
.create_descriptor_set_layout(&descriptor_info, None) .create_descriptor_set_layout(&descriptor_info, None)
.unwrap()]; .unwrap()];
let desc_alloc_info = vk::DescriptorSetAllocateInfo {
s_type: vk::StructureType::DESCRIPTOR_SET_ALLOCATE_INFO, let desc_alloc_info = vk::DescriptorSetAllocateInfo::builder()
p_next: ptr::null(), .descriptor_pool(descriptor_pool)
descriptor_pool: descriptor_pool, .set_layouts(&desc_set_layouts);
descriptor_set_count: desc_set_layouts.len() as u32,
p_set_layouts: desc_set_layouts.as_ptr(),
};
let descriptor_sets = base let descriptor_sets = base
.device .device
.allocate_descriptor_sets(&desc_alloc_info) .allocate_descriptor_sets(&desc_alloc_info)
@ -610,63 +523,43 @@ fn main() {
}; };
let tex_descriptor = vk::DescriptorImageInfo { let tex_descriptor = vk::DescriptorImageInfo {
image_layout: vk::ImageLayout::GENERAL, image_layout: vk::ImageLayout::SHADER_READ_ONLY_OPTIMAL,
image_view: tex_image_view, image_view: tex_image_view,
sampler: sampler, sampler: sampler,
}; };
let write_desc_sets = [ let write_desc_sets = [
vk::WriteDescriptorSet { vk::WriteDescriptorSet {
s_type: vk::StructureType::WRITE_DESCRIPTOR_SET,
p_next: ptr::null(),
dst_set: descriptor_sets[0], dst_set: descriptor_sets[0],
dst_binding: 0,
dst_array_element: 0,
descriptor_count: 1, descriptor_count: 1,
descriptor_type: vk::DescriptorType::UNIFORM_BUFFER, descriptor_type: vk::DescriptorType::UNIFORM_BUFFER,
p_image_info: ptr::null(),
p_buffer_info: &uniform_color_buffer_descriptor, p_buffer_info: &uniform_color_buffer_descriptor,
p_texel_buffer_view: ptr::null(), ..Default::default()
}, },
vk::WriteDescriptorSet { vk::WriteDescriptorSet {
s_type: vk::StructureType::WRITE_DESCRIPTOR_SET,
p_next: ptr::null(),
dst_set: descriptor_sets[0], dst_set: descriptor_sets[0],
dst_binding: 1, dst_binding: 1,
dst_array_element: 0,
descriptor_count: 1, descriptor_count: 1,
descriptor_type: vk::DescriptorType::COMBINED_IMAGE_SAMPLER, descriptor_type: vk::DescriptorType::COMBINED_IMAGE_SAMPLER,
p_image_info: &tex_descriptor, p_image_info: &tex_descriptor,
p_buffer_info: ptr::null(), ..Default::default()
p_texel_buffer_view: ptr::null(),
}, },
]; ];
base.device.update_descriptor_sets(&write_desc_sets, &[]); base.device.update_descriptor_sets(&write_desc_sets, &[]);
let vertex_spv_file = let mut vertex_spv_file =
File::open(Path::new("shader/texture/vert.spv")).expect("Could not find vert.spv."); File::open(Path::new("shader/texture/vert.spv")).expect("Could not find vert.spv.");
let frag_spv_file = let mut frag_spv_file =
File::open(Path::new("shader/texture/frag.spv")).expect("Could not find frag.spv."); File::open(Path::new("shader/texture/frag.spv")).expect("Could not find frag.spv.");
let vertex_bytes: Vec<u8> = vertex_spv_file let vertex_code =
.bytes() read_spv(&mut vertex_spv_file).expect("Failed to read vertex shader spv file");
.filter_map(|byte| byte.ok()) let vertex_shader_info = vk::ShaderModuleCreateInfo::builder().code(&vertex_code);
.collect();
let vertex_shader_info = vk::ShaderModuleCreateInfo { let frag_code =
s_type: vk::StructureType::SHADER_MODULE_CREATE_INFO, read_spv(&mut frag_spv_file).expect("Failed to read fragment shader spv file");
p_next: ptr::null(), let frag_shader_info = vk::ShaderModuleCreateInfo::builder().code(&frag_code);
flags: Default::default(),
code_size: vertex_bytes.len(),
p_code: vertex_bytes.as_ptr() as *const u32,
};
let frag_bytes: Vec<u8> = frag_spv_file.bytes().filter_map(|byte| byte.ok()).collect();
let frag_shader_info = vk::ShaderModuleCreateInfo {
s_type: vk::StructureType::SHADER_MODULE_CREATE_INFO,
p_next: ptr::null(),
flags: Default::default(),
code_size: frag_bytes.len(),
p_code: frag_bytes.as_ptr() as *const u32,
};
let vertex_shader_module = base let vertex_shader_module = base
.device .device
.create_shader_module(&vertex_shader_info, None) .create_shader_module(&vertex_shader_info, None)
@ -677,15 +570,8 @@ fn main() {
.create_shader_module(&frag_shader_info, None) .create_shader_module(&frag_shader_info, None)
.expect("Fragment shader module error"); .expect("Fragment shader module error");
let layout_create_info = vk::PipelineLayoutCreateInfo { let layout_create_info =
s_type: vk::StructureType::PIPELINE_LAYOUT_CREATE_INFO, vk::PipelineLayoutCreateInfo::builder().set_layouts(&desc_set_layouts);
p_next: ptr::null(),
flags: Default::default(),
set_layout_count: desc_set_layouts.len() as u32,
p_set_layouts: desc_set_layouts.as_ptr(),
push_constant_range_count: 0,
p_push_constant_ranges: ptr::null(),
};
let pipeline_layout = base let pipeline_layout = base
.device .device
@ -695,22 +581,16 @@ fn main() {
let shader_entry_name = CString::new("main").unwrap(); let shader_entry_name = CString::new("main").unwrap();
let shader_stage_create_infos = [ let shader_stage_create_infos = [
vk::PipelineShaderStageCreateInfo { vk::PipelineShaderStageCreateInfo {
s_type: vk::StructureType::PIPELINE_SHADER_STAGE_CREATE_INFO,
p_next: ptr::null(),
flags: Default::default(),
module: vertex_shader_module, module: vertex_shader_module,
p_name: shader_entry_name.as_ptr(), p_name: shader_entry_name.as_ptr(),
p_specialization_info: ptr::null(),
stage: vk::ShaderStageFlags::VERTEX, stage: vk::ShaderStageFlags::VERTEX,
..Default::default()
}, },
vk::PipelineShaderStageCreateInfo { vk::PipelineShaderStageCreateInfo {
s_type: vk::StructureType::PIPELINE_SHADER_STAGE_CREATE_INFO,
p_next: ptr::null(),
flags: Default::default(),
module: fragment_shader_module, module: fragment_shader_module,
p_name: shader_entry_name.as_ptr(), p_name: shader_entry_name.as_ptr(),
p_specialization_info: ptr::null(),
stage: vk::ShaderStageFlags::FRAGMENT, stage: vk::ShaderStageFlags::FRAGMENT,
..Default::default()
}, },
]; ];
let vertex_input_binding_descriptions = [vk::VertexInputBindingDescription { let vertex_input_binding_descriptions = [vk::VertexInputBindingDescription {
@ -732,21 +612,13 @@ fn main() {
offset: offset_of!(Vertex, uv) as u32, offset: offset_of!(Vertex, uv) as u32,
}, },
]; ];
let vertex_input_state_info = vk::PipelineVertexInputStateCreateInfo { let vertex_input_state_info = vk::PipelineVertexInputStateCreateInfo::builder()
s_type: vk::StructureType::PIPELINE_VERTEX_INPUT_STATE_CREATE_INFO, .vertex_attribute_descriptions(&vertex_input_attribute_descriptions)
p_next: ptr::null(), .vertex_binding_descriptions(&vertex_input_binding_descriptions);
flags: Default::default(),
vertex_attribute_description_count: vertex_input_attribute_descriptions.len() as u32,
p_vertex_attribute_descriptions: vertex_input_attribute_descriptions.as_ptr(),
vertex_binding_description_count: vertex_input_binding_descriptions.len() as u32,
p_vertex_binding_descriptions: vertex_input_binding_descriptions.as_ptr(),
};
let vertex_input_assembly_state_info = vk::PipelineInputAssemblyStateCreateInfo { let vertex_input_assembly_state_info = vk::PipelineInputAssemblyStateCreateInfo {
s_type: vk::StructureType::PIPELINE_INPUT_ASSEMBLY_STATE_CREATE_INFO,
flags: Default::default(),
p_next: ptr::null(),
primitive_restart_enable: 0,
topology: vk::PrimitiveTopology::TRIANGLE_LIST, topology: vk::PrimitiveTopology::TRIANGLE_LIST,
..Default::default()
}; };
let viewports = [vk::Viewport { let viewports = [vk::Viewport {
x: 0.0, x: 0.0,
@ -757,67 +629,40 @@ fn main() {
max_depth: 1.0, max_depth: 1.0,
}]; }];
let scissors = [vk::Rect2D { let scissors = [vk::Rect2D {
offset: vk::Offset2D { x: 0, y: 0 },
extent: base.surface_resolution.clone(), extent: base.surface_resolution.clone(),
..Default::default()
}]; }];
let viewport_state_info = vk::PipelineViewportStateCreateInfo { let viewport_state_info = vk::PipelineViewportStateCreateInfo::builder()
s_type: vk::StructureType::PIPELINE_VIEWPORT_STATE_CREATE_INFO, .scissors(&scissors)
p_next: ptr::null(), .viewports(&viewports);
flags: Default::default(),
scissor_count: scissors.len() as u32,
p_scissors: scissors.as_ptr(),
viewport_count: viewports.len() as u32,
p_viewports: viewports.as_ptr(),
};
let rasterization_info = vk::PipelineRasterizationStateCreateInfo { let rasterization_info = vk::PipelineRasterizationStateCreateInfo {
s_type: vk::StructureType::PIPELINE_RASTERIZATION_STATE_CREATE_INFO,
p_next: ptr::null(),
flags: Default::default(),
cull_mode: vk::CullModeFlags::NONE,
depth_bias_clamp: 0.0,
depth_bias_constant_factor: 0.0,
depth_bias_enable: 0,
depth_bias_slope_factor: 0.0,
depth_clamp_enable: 0,
front_face: vk::FrontFace::COUNTER_CLOCKWISE, front_face: vk::FrontFace::COUNTER_CLOCKWISE,
line_width: 1.0, line_width: 1.0,
polygon_mode: vk::PolygonMode::FILL, polygon_mode: vk::PolygonMode::FILL,
rasterizer_discard_enable: 0, ..Default::default()
};
let multisample_state_info = vk::PipelineMultisampleStateCreateInfo {
s_type: vk::StructureType::PIPELINE_MULTISAMPLE_STATE_CREATE_INFO,
flags: Default::default(),
p_next: ptr::null(),
rasterization_samples: vk::SampleCountFlags::TYPE_1,
sample_shading_enable: 0,
min_sample_shading: 0.0,
p_sample_mask: ptr::null(),
alpha_to_one_enable: 0,
alpha_to_coverage_enable: 0,
}; };
let multisample_state_info = vk::PipelineMultisampleStateCreateInfo::builder()
.rasterization_samples(vk::SampleCountFlags::TYPE_1);
let noop_stencil_state = vk::StencilOpState { let noop_stencil_state = vk::StencilOpState {
fail_op: vk::StencilOp::KEEP, fail_op: vk::StencilOp::KEEP,
pass_op: vk::StencilOp::KEEP, pass_op: vk::StencilOp::KEEP,
depth_fail_op: vk::StencilOp::KEEP, depth_fail_op: vk::StencilOp::KEEP,
compare_op: vk::CompareOp::ALWAYS, compare_op: vk::CompareOp::ALWAYS,
compare_mask: 0, ..Default::default()
write_mask: 0,
reference: 0,
}; };
let depth_state_info = vk::PipelineDepthStencilStateCreateInfo { let depth_state_info = vk::PipelineDepthStencilStateCreateInfo {
s_type: vk::StructureType::PIPELINE_DEPTH_STENCIL_STATE_CREATE_INFO,
p_next: ptr::null(),
flags: Default::default(),
depth_test_enable: 1, depth_test_enable: 1,
depth_write_enable: 1, depth_write_enable: 1,
depth_compare_op: vk::CompareOp::LESS_OR_EQUAL, depth_compare_op: vk::CompareOp::LESS_OR_EQUAL,
depth_bounds_test_enable: 0,
stencil_test_enable: 0,
front: noop_stencil_state.clone(), front: noop_stencil_state.clone(),
back: noop_stencil_state.clone(), back: noop_stencil_state.clone(),
max_depth_bounds: 1.0, max_depth_bounds: 1.0,
min_depth_bounds: 0.0, ..Default::default()
}; };
let color_blend_attachment_states = [vk::PipelineColorBlendAttachmentState { let color_blend_attachment_states = [vk::PipelineColorBlendAttachmentState {
blend_enable: 0, blend_enable: 0,
src_color_blend_factor: vk::BlendFactor::SRC_COLOR, src_color_blend_factor: vk::BlendFactor::SRC_COLOR,
@ -828,48 +673,34 @@ fn main() {
alpha_blend_op: vk::BlendOp::ADD, alpha_blend_op: vk::BlendOp::ADD,
color_write_mask: vk::ColorComponentFlags::all(), color_write_mask: vk::ColorComponentFlags::all(),
}]; }];
let color_blend_state = vk::PipelineColorBlendStateCreateInfo { let color_blend_state = vk::PipelineColorBlendStateCreateInfo::builder()
s_type: vk::StructureType::PIPELINE_COLOR_BLEND_STATE_CREATE_INFO, .logic_op(vk::LogicOp::CLEAR)
p_next: ptr::null(), .attachments(&color_blend_attachment_states);
flags: Default::default(),
logic_op_enable: 0,
logic_op: vk::LogicOp::CLEAR,
attachment_count: color_blend_attachment_states.len() as u32,
p_attachments: color_blend_attachment_states.as_ptr(),
blend_constants: [0.0, 0.0, 0.0, 0.0],
};
let dynamic_state = [vk::DynamicState::VIEWPORT, vk::DynamicState::SCISSOR]; let dynamic_state = [vk::DynamicState::VIEWPORT, vk::DynamicState::SCISSOR];
let dynamic_state_info = vk::PipelineDynamicStateCreateInfo { let dynamic_state_info =
s_type: vk::StructureType::PIPELINE_DYNAMIC_STATE_CREATE_INFO, vk::PipelineDynamicStateCreateInfo::builder().dynamic_states(&dynamic_state);
p_next: ptr::null(),
flags: Default::default(), let graphic_pipeline_infos = vk::GraphicsPipelineCreateInfo::builder()
dynamic_state_count: dynamic_state.len() as u32, .stages(&shader_stage_create_infos)
p_dynamic_states: dynamic_state.as_ptr(), .vertex_input_state(&vertex_input_state_info)
}; .input_assembly_state(&vertex_input_assembly_state_info)
let graphic_pipeline_info = vk::GraphicsPipelineCreateInfo { .viewport_state(&viewport_state_info)
s_type: vk::StructureType::GRAPHICS_PIPELINE_CREATE_INFO, .rasterization_state(&rasterization_info)
p_next: ptr::null(), .multisample_state(&multisample_state_info)
flags: vk::PipelineCreateFlags::empty(), .depth_stencil_state(&depth_state_info)
stage_count: shader_stage_create_infos.len() as u32, .color_blend_state(&color_blend_state)
p_stages: shader_stage_create_infos.as_ptr(), .dynamic_state(&dynamic_state_info)
p_vertex_input_state: &vertex_input_state_info, .layout(pipeline_layout)
p_input_assembly_state: &vertex_input_assembly_state_info, .render_pass(renderpass);
p_tessellation_state: ptr::null(),
p_viewport_state: &viewport_state_info,
p_rasterization_state: &rasterization_info,
p_multisample_state: &multisample_state_info,
p_depth_stencil_state: &depth_state_info,
p_color_blend_state: &color_blend_state,
p_dynamic_state: &dynamic_state_info,
layout: pipeline_layout,
render_pass: renderpass,
subpass: 0,
base_pipeline_handle: vk::Pipeline::null(),
base_pipeline_index: 0,
};
let graphics_pipelines = base let graphics_pipelines = base
.device .device
.create_graphics_pipelines(vk::PipelineCache::null(), &[graphic_pipeline_info], None) .create_graphics_pipelines(
vk::PipelineCache::null(),
&[graphic_pipeline_infos.build()],
None,
)
.unwrap(); .unwrap();
let graphic_pipeline = graphics_pipelines[0]; let graphic_pipeline = graphics_pipelines[0];
@ -877,7 +708,7 @@ fn main() {
base.render_loop(|| { base.render_loop(|| {
let (present_index, _) = base let (present_index, _) = base
.swapchain_loader .swapchain_loader
.acquire_next_image_khr( .acquire_next_image(
base.swapchain, base.swapchain,
std::u64::MAX, std::u64::MAX,
base.present_complete_semaphore, base.present_complete_semaphore,
@ -898,18 +729,15 @@ fn main() {
}, },
]; ];
let render_pass_begin_info = vk::RenderPassBeginInfo { let render_pass_begin_info = vk::RenderPassBeginInfo::builder()
s_type: vk::StructureType::RENDER_PASS_BEGIN_INFO, .render_pass(renderpass)
p_next: ptr::null(), .framebuffer(framebuffers[present_index as usize])
render_pass: renderpass, .render_area(vk::Rect2D {
framebuffer: framebuffers[present_index as usize],
render_area: vk::Rect2D {
offset: vk::Offset2D { x: 0, y: 0 }, offset: vk::Offset2D { x: 0, y: 0 },
extent: base.surface_resolution.clone(), extent: base.surface_resolution.clone(),
}, })
clear_value_count: clear_values.len() as u32, .clear_values(&clear_values);
p_clear_values: clear_values.as_ptr(),
};
record_submit_commandbuffer( record_submit_commandbuffer(
&base.device, &base.device,
base.draw_command_buffer, base.draw_command_buffer,
@ -965,17 +793,15 @@ fn main() {
); );
//let mut present_info_err = mem::uninitialized(); //let mut present_info_err = mem::uninitialized();
let present_info = vk::PresentInfoKHR { let present_info = vk::PresentInfoKHR {
s_type: vk::StructureType::PRESENT_INFO_KHR,
p_next: ptr::null(),
wait_semaphore_count: 1, wait_semaphore_count: 1,
p_wait_semaphores: &base.rendering_complete_semaphore, p_wait_semaphores: &base.rendering_complete_semaphore,
swapchain_count: 1, swapchain_count: 1,
p_swapchains: &base.swapchain, p_swapchains: &base.swapchain,
p_image_indices: &present_index, p_image_indices: &present_index,
p_results: ptr::null_mut(), ..Default::default()
}; };
base.swapchain_loader base.swapchain_loader
.queue_present_khr(base.present_queue, &present_info) .queue_present(base.present_queue, &present_info)
.unwrap(); .unwrap();
}); });
base.device.device_wait_idle().unwrap(); base.device.device_wait_idle().unwrap();

View file

@ -7,11 +7,9 @@ use examples::*;
use std::default::Default; use std::default::Default;
use std::ffi::CString; use std::ffi::CString;
use std::fs::File; use std::fs::File;
use std::io::Read;
use std::mem; use std::mem;
use std::mem::align_of; use std::mem::align_of;
use std::path::Path; use std::path::Path;
use std::ptr;
#[derive(Clone, Debug, Copy)] #[derive(Clone, Debug, Copy)]
struct Vertex { struct Vertex {
@ -25,117 +23,91 @@ fn main() {
let renderpass_attachments = [ let renderpass_attachments = [
vk::AttachmentDescription { vk::AttachmentDescription {
format: base.surface_format.format, format: base.surface_format.format,
flags: vk::AttachmentDescriptionFlags::empty(),
samples: vk::SampleCountFlags::TYPE_1, samples: vk::SampleCountFlags::TYPE_1,
load_op: vk::AttachmentLoadOp::CLEAR, load_op: vk::AttachmentLoadOp::CLEAR,
store_op: vk::AttachmentStoreOp::STORE, store_op: vk::AttachmentStoreOp::STORE,
stencil_load_op: vk::AttachmentLoadOp::DONT_CARE,
stencil_store_op: vk::AttachmentStoreOp::DONT_CARE,
initial_layout: vk::ImageLayout::UNDEFINED,
final_layout: vk::ImageLayout::PRESENT_SRC_KHR, final_layout: vk::ImageLayout::PRESENT_SRC_KHR,
..Default::default()
}, },
vk::AttachmentDescription { vk::AttachmentDescription {
format: vk::Format::D16_UNORM, format: vk::Format::D16_UNORM,
flags: vk::AttachmentDescriptionFlags::empty(),
samples: vk::SampleCountFlags::TYPE_1, samples: vk::SampleCountFlags::TYPE_1,
load_op: vk::AttachmentLoadOp::CLEAR, load_op: vk::AttachmentLoadOp::CLEAR,
store_op: vk::AttachmentStoreOp::DONT_CARE,
stencil_load_op: vk::AttachmentLoadOp::DONT_CARE,
stencil_store_op: vk::AttachmentStoreOp::DONT_CARE,
initial_layout: vk::ImageLayout::DEPTH_STENCIL_ATTACHMENT_OPTIMAL, initial_layout: vk::ImageLayout::DEPTH_STENCIL_ATTACHMENT_OPTIMAL,
final_layout: vk::ImageLayout::DEPTH_STENCIL_ATTACHMENT_OPTIMAL, final_layout: vk::ImageLayout::DEPTH_STENCIL_ATTACHMENT_OPTIMAL,
..Default::default()
}, },
]; ];
let color_attachment_ref = vk::AttachmentReference { let color_attachment_refs = [vk::AttachmentReference {
attachment: 0, attachment: 0,
layout: vk::ImageLayout::COLOR_ATTACHMENT_OPTIMAL, layout: vk::ImageLayout::COLOR_ATTACHMENT_OPTIMAL,
}; }];
let depth_attachment_ref = vk::AttachmentReference { let depth_attachment_ref = vk::AttachmentReference {
attachment: 1, attachment: 1,
layout: vk::ImageLayout::DEPTH_STENCIL_ATTACHMENT_OPTIMAL, layout: vk::ImageLayout::DEPTH_STENCIL_ATTACHMENT_OPTIMAL,
}; };
let dependency = vk::SubpassDependency { let dependencies = [vk::SubpassDependency {
dependency_flags: Default::default(),
src_subpass: vk::SUBPASS_EXTERNAL, src_subpass: vk::SUBPASS_EXTERNAL,
dst_subpass: Default::default(),
src_stage_mask: vk::PipelineStageFlags::COLOR_ATTACHMENT_OUTPUT, src_stage_mask: vk::PipelineStageFlags::COLOR_ATTACHMENT_OUTPUT,
src_access_mask: Default::default(),
dst_access_mask: vk::AccessFlags::COLOR_ATTACHMENT_READ dst_access_mask: vk::AccessFlags::COLOR_ATTACHMENT_READ
| vk::AccessFlags::COLOR_ATTACHMENT_WRITE, | vk::AccessFlags::COLOR_ATTACHMENT_WRITE,
dst_stage_mask: vk::PipelineStageFlags::COLOR_ATTACHMENT_OUTPUT, dst_stage_mask: vk::PipelineStageFlags::COLOR_ATTACHMENT_OUTPUT,
}; ..Default::default()
let subpass = vk::SubpassDescription { }];
color_attachment_count: 1,
p_color_attachments: &color_attachment_ref, let subpasses = [vk::SubpassDescription::builder()
p_depth_stencil_attachment: &depth_attachment_ref, .color_attachments(&color_attachment_refs)
flags: Default::default(), .depth_stencil_attachment(&depth_attachment_ref)
pipeline_bind_point: vk::PipelineBindPoint::GRAPHICS, .pipeline_bind_point(vk::PipelineBindPoint::GRAPHICS)
input_attachment_count: 0, .build()];
p_input_attachments: ptr::null(),
p_resolve_attachments: ptr::null(), let renderpass_create_info = vk::RenderPassCreateInfo::builder()
preserve_attachment_count: 0, .attachments(&renderpass_attachments)
p_preserve_attachments: ptr::null(), .subpasses(&subpasses)
}; .dependencies(&dependencies);
let renderpass_create_info = vk::RenderPassCreateInfo {
s_type: vk::StructureType::RENDER_PASS_CREATE_INFO,
flags: Default::default(),
p_next: ptr::null(),
attachment_count: renderpass_attachments.len() as u32,
p_attachments: renderpass_attachments.as_ptr(),
subpass_count: 1,
p_subpasses: &subpass,
dependency_count: 1,
p_dependencies: &dependency,
};
let renderpass = base let renderpass = base
.device .device
.create_render_pass(&renderpass_create_info, None) .create_render_pass(&renderpass_create_info, None)
.unwrap(); .unwrap();
let framebuffers: Vec<vk::Framebuffer> = base let framebuffers: Vec<vk::Framebuffer> = base
.present_image_views .present_image_views
.iter() .iter()
.map(|&present_image_view| { .map(|&present_image_view| {
let framebuffer_attachments = [present_image_view, base.depth_image_view]; let framebuffer_attachments = [present_image_view, base.depth_image_view];
let frame_buffer_create_info = vk::FramebufferCreateInfo { let frame_buffer_create_info = vk::FramebufferCreateInfo::builder()
s_type: vk::StructureType::FRAMEBUFFER_CREATE_INFO, .render_pass(renderpass)
p_next: ptr::null(), .attachments(&framebuffer_attachments)
flags: Default::default(), .width(base.surface_resolution.width)
render_pass: renderpass, .height(base.surface_resolution.height)
attachment_count: framebuffer_attachments.len() as u32, .layers(1);
p_attachments: framebuffer_attachments.as_ptr(),
width: base.surface_resolution.width,
height: base.surface_resolution.height,
layers: 1,
};
base.device base.device
.create_framebuffer(&frame_buffer_create_info, None) .create_framebuffer(&frame_buffer_create_info, None)
.unwrap() .unwrap()
}) })
.collect(); .collect();
let index_buffer_data = [0u32, 1, 2]; let index_buffer_data = [0u32, 1, 2];
let index_buffer_info = vk::BufferCreateInfo { let index_buffer_info = vk::BufferCreateInfo::builder()
s_type: vk::StructureType::BUFFER_CREATE_INFO, .size(std::mem::size_of_val(&index_buffer_data) as u64)
p_next: ptr::null(), .usage(vk::BufferUsageFlags::INDEX_BUFFER)
flags: vk::BufferCreateFlags::empty(), .sharing_mode(vk::SharingMode::EXCLUSIVE);
size: std::mem::size_of_val(&index_buffer_data) as u64,
usage: vk::BufferUsageFlags::INDEX_BUFFER,
sharing_mode: vk::SharingMode::EXCLUSIVE,
queue_family_index_count: 0,
p_queue_family_indices: ptr::null(),
};
let index_buffer = base.device.create_buffer(&index_buffer_info, None).unwrap(); let index_buffer = base.device.create_buffer(&index_buffer_info, None).unwrap();
let index_buffer_memory_req = base.device.get_buffer_memory_requirements(index_buffer); let index_buffer_memory_req = base.device.get_buffer_memory_requirements(index_buffer);
let index_buffer_memory_index = let index_buffer_memory_index = find_memorytype_index(
find_memorytype_index( &index_buffer_memory_req,
&index_buffer_memory_req, &base.device_memory_properties,
&base.device_memory_properties, vk::MemoryPropertyFlags::HOST_VISIBLE,
vk::MemoryPropertyFlags::HOST_VISIBLE, )
).expect("Unable to find suitable memorytype for the index buffer."); .expect("Unable to find suitable memorytype for the index buffer.");
let index_allocate_info = vk::MemoryAllocateInfo { let index_allocate_info = vk::MemoryAllocateInfo {
s_type: vk::StructureType::MEMORY_ALLOCATE_INFO,
p_next: ptr::null(),
allocation_size: index_buffer_memory_req.size, allocation_size: index_buffer_memory_req.size,
memory_type_index: index_buffer_memory_index, memory_type_index: index_buffer_memory_index,
..Default::default()
}; };
let index_buffer_memory = base let index_buffer_memory = base
.device .device
@ -162,39 +134,39 @@ fn main() {
.unwrap(); .unwrap();
let vertex_input_buffer_info = vk::BufferCreateInfo { let vertex_input_buffer_info = vk::BufferCreateInfo {
s_type: vk::StructureType::BUFFER_CREATE_INFO,
p_next: ptr::null(),
flags: vk::BufferCreateFlags::empty(),
size: 3 * std::mem::size_of::<Vertex>() as u64, size: 3 * std::mem::size_of::<Vertex>() as u64,
usage: vk::BufferUsageFlags::VERTEX_BUFFER, usage: vk::BufferUsageFlags::VERTEX_BUFFER,
sharing_mode: vk::SharingMode::EXCLUSIVE, sharing_mode: vk::SharingMode::EXCLUSIVE,
queue_family_index_count: 0, ..Default::default()
p_queue_family_indices: ptr::null(),
}; };
let vertex_input_buffer = base let vertex_input_buffer = base
.device .device
.create_buffer(&vertex_input_buffer_info, None) .create_buffer(&vertex_input_buffer_info, None)
.unwrap(); .unwrap();
let vertex_input_buffer_memory_req = base let vertex_input_buffer_memory_req = base
.device .device
.get_buffer_memory_requirements(vertex_input_buffer); .get_buffer_memory_requirements(vertex_input_buffer);
let vertex_input_buffer_memory_index =
find_memorytype_index( let vertex_input_buffer_memory_index = find_memorytype_index(
&vertex_input_buffer_memory_req, &vertex_input_buffer_memory_req,
&base.device_memory_properties, &base.device_memory_properties,
vk::MemoryPropertyFlags::HOST_VISIBLE, vk::MemoryPropertyFlags::HOST_VISIBLE,
).expect("Unable to find suitable memorytype for the vertex buffer."); )
.expect("Unable to find suitable memorytype for the vertex buffer.");
let vertex_buffer_allocate_info = vk::MemoryAllocateInfo { let vertex_buffer_allocate_info = vk::MemoryAllocateInfo {
s_type: vk::StructureType::MEMORY_ALLOCATE_INFO,
p_next: ptr::null(),
allocation_size: vertex_input_buffer_memory_req.size, allocation_size: vertex_input_buffer_memory_req.size,
memory_type_index: vertex_input_buffer_memory_index, memory_type_index: vertex_input_buffer_memory_index,
..Default::default()
}; };
let vertex_input_buffer_memory = base let vertex_input_buffer_memory = base
.device .device
.allocate_memory(&vertex_buffer_allocate_info, None) .allocate_memory(&vertex_buffer_allocate_info, None)
.unwrap(); .unwrap();
let vertices = [ let vertices = [
Vertex { Vertex {
pos: [-1.0, 1.0, 0.0, 1.0], pos: [-1.0, 1.0, 0.0, 1.0],
@ -209,6 +181,7 @@ fn main() {
color: [1.0, 0.0, 0.0, 1.0], color: [1.0, 0.0, 0.0, 1.0],
}, },
]; ];
let vert_ptr = base let vert_ptr = base
.device .device
.map_memory( .map_memory(
@ -218,6 +191,7 @@ fn main() {
vk::MemoryMapFlags::empty(), vk::MemoryMapFlags::empty(),
) )
.unwrap(); .unwrap();
let mut vert_align = Align::new( let mut vert_align = Align::new(
vert_ptr, vert_ptr,
align_of::<Vertex>() as u64, align_of::<Vertex>() as u64,
@ -228,30 +202,19 @@ fn main() {
base.device base.device
.bind_buffer_memory(vertex_input_buffer, vertex_input_buffer_memory, 0) .bind_buffer_memory(vertex_input_buffer, vertex_input_buffer_memory, 0)
.unwrap(); .unwrap();
let vertex_spv_file = let mut vertex_spv_file =
File::open(Path::new("shader/triangle/vert.spv")).expect("Could not find vert.spv."); File::open(Path::new("shader/triangle/vert.spv")).expect("Could not find vert.spv.");
let frag_spv_file = let mut frag_spv_file =
File::open(Path::new("shader/triangle/frag.spv")).expect("Could not find frag.spv."); File::open(Path::new("shader/triangle/frag.spv")).expect("Could not find frag.spv.");
let vertex_bytes: Vec<u8> = vertex_spv_file let vertex_code =
.bytes() read_spv(&mut vertex_spv_file).expect("Failed to read vertex shader spv file");
.filter_map(|byte| byte.ok()) let vertex_shader_info = vk::ShaderModuleCreateInfo::builder().code(&vertex_code);
.collect();
let vertex_shader_info = vk::ShaderModuleCreateInfo { let frag_code =
s_type: vk::StructureType::SHADER_MODULE_CREATE_INFO, read_spv(&mut frag_spv_file).expect("Failed to read fragment shader spv file");
p_next: ptr::null(), let frag_shader_info = vk::ShaderModuleCreateInfo::builder().code(&frag_code);
flags: Default::default(),
code_size: vertex_bytes.len(),
p_code: vertex_bytes.as_ptr() as *const u32,
};
let frag_bytes: Vec<u8> = frag_spv_file.bytes().filter_map(|byte| byte.ok()).collect();
let frag_shader_info = vk::ShaderModuleCreateInfo {
s_type: vk::StructureType::SHADER_MODULE_CREATE_INFO,
p_next: ptr::null(),
flags: Default::default(),
code_size: frag_bytes.len(),
p_code: frag_bytes.as_ptr() as *const u32,
};
let vertex_shader_module = base let vertex_shader_module = base
.device .device
.create_shader_module(&vertex_shader_info, None) .create_shader_module(&vertex_shader_info, None)
@ -262,15 +225,7 @@ fn main() {
.create_shader_module(&frag_shader_info, None) .create_shader_module(&frag_shader_info, None)
.expect("Fragment shader module error"); .expect("Fragment shader module error");
let layout_create_info = vk::PipelineLayoutCreateInfo { let layout_create_info = vk::PipelineLayoutCreateInfo::default();
s_type: vk::StructureType::PIPELINE_LAYOUT_CREATE_INFO,
p_next: ptr::null(),
flags: Default::default(),
set_layout_count: 0,
p_set_layouts: ptr::null(),
push_constant_range_count: 0,
p_push_constant_ranges: ptr::null(),
};
let pipeline_layout = base let pipeline_layout = base
.device .device
@ -280,22 +235,17 @@ fn main() {
let shader_entry_name = CString::new("main").unwrap(); let shader_entry_name = CString::new("main").unwrap();
let shader_stage_create_infos = [ let shader_stage_create_infos = [
vk::PipelineShaderStageCreateInfo { vk::PipelineShaderStageCreateInfo {
s_type: vk::StructureType::PIPELINE_SHADER_STAGE_CREATE_INFO,
p_next: ptr::null(),
flags: Default::default(),
module: vertex_shader_module, module: vertex_shader_module,
p_name: shader_entry_name.as_ptr(), p_name: shader_entry_name.as_ptr(),
p_specialization_info: ptr::null(),
stage: vk::ShaderStageFlags::VERTEX, stage: vk::ShaderStageFlags::VERTEX,
..Default::default()
}, },
vk::PipelineShaderStageCreateInfo { vk::PipelineShaderStageCreateInfo {
s_type: vk::StructureType::PIPELINE_SHADER_STAGE_CREATE_INFO, s_type: vk::StructureType::PIPELINE_SHADER_STAGE_CREATE_INFO,
p_next: ptr::null(),
flags: Default::default(),
module: fragment_shader_module, module: fragment_shader_module,
p_name: shader_entry_name.as_ptr(), p_name: shader_entry_name.as_ptr(),
p_specialization_info: ptr::null(),
stage: vk::ShaderStageFlags::FRAGMENT, stage: vk::ShaderStageFlags::FRAGMENT,
..Default::default()
}, },
]; ];
let vertex_input_binding_descriptions = [vk::VertexInputBindingDescription { let vertex_input_binding_descriptions = [vk::VertexInputBindingDescription {
@ -317,21 +267,17 @@ fn main() {
offset: offset_of!(Vertex, color) as u32, offset: offset_of!(Vertex, color) as u32,
}, },
]; ];
let vertex_input_state_info = vk::PipelineVertexInputStateCreateInfo { let vertex_input_state_info = vk::PipelineVertexInputStateCreateInfo {
s_type: vk::StructureType::PIPELINE_VERTEX_INPUT_STATE_CREATE_INFO,
p_next: ptr::null(),
flags: Default::default(),
vertex_attribute_description_count: vertex_input_attribute_descriptions.len() as u32, vertex_attribute_description_count: vertex_input_attribute_descriptions.len() as u32,
p_vertex_attribute_descriptions: vertex_input_attribute_descriptions.as_ptr(), p_vertex_attribute_descriptions: vertex_input_attribute_descriptions.as_ptr(),
vertex_binding_description_count: vertex_input_binding_descriptions.len() as u32, vertex_binding_description_count: vertex_input_binding_descriptions.len() as u32,
p_vertex_binding_descriptions: vertex_input_binding_descriptions.as_ptr(), p_vertex_binding_descriptions: vertex_input_binding_descriptions.as_ptr(),
..Default::default()
}; };
let vertex_input_assembly_state_info = vk::PipelineInputAssemblyStateCreateInfo { let vertex_input_assembly_state_info = vk::PipelineInputAssemblyStateCreateInfo {
s_type: vk::StructureType::PIPELINE_INPUT_ASSEMBLY_STATE_CREATE_INFO,
flags: Default::default(),
p_next: ptr::null(),
primitive_restart_enable: 0,
topology: vk::PrimitiveTopology::TRIANGLE_LIST, topology: vk::PrimitiveTopology::TRIANGLE_LIST,
..Default::default()
}; };
let viewports = [vk::Viewport { let viewports = [vk::Viewport {
x: 0.0, x: 0.0,
@ -345,63 +291,35 @@ fn main() {
offset: vk::Offset2D { x: 0, y: 0 }, offset: vk::Offset2D { x: 0, y: 0 },
extent: base.surface_resolution.clone(), extent: base.surface_resolution.clone(),
}]; }];
let viewport_state_info = vk::PipelineViewportStateCreateInfo { let viewport_state_info = vk::PipelineViewportStateCreateInfo::builder()
s_type: vk::StructureType::PIPELINE_VIEWPORT_STATE_CREATE_INFO, .scissors(&scissors)
p_next: ptr::null(), .viewports(&viewports);
flags: Default::default(),
scissor_count: scissors.len() as u32,
p_scissors: scissors.as_ptr(),
viewport_count: viewports.len() as u32,
p_viewports: viewports.as_ptr(),
};
let rasterization_info = vk::PipelineRasterizationStateCreateInfo { let rasterization_info = vk::PipelineRasterizationStateCreateInfo {
s_type: vk::StructureType::PIPELINE_RASTERIZATION_STATE_CREATE_INFO,
p_next: ptr::null(),
flags: Default::default(),
cull_mode: vk::CullModeFlags::NONE,
depth_bias_clamp: 0.0,
depth_bias_constant_factor: 0.0,
depth_bias_enable: 0,
depth_bias_slope_factor: 0.0,
depth_clamp_enable: 0,
front_face: vk::FrontFace::COUNTER_CLOCKWISE, front_face: vk::FrontFace::COUNTER_CLOCKWISE,
line_width: 1.0, line_width: 1.0,
polygon_mode: vk::PolygonMode::FILL, polygon_mode: vk::PolygonMode::FILL,
rasterizer_discard_enable: 0, ..Default::default()
}; };
let multisample_state_info = vk::PipelineMultisampleStateCreateInfo { let multisample_state_info = vk::PipelineMultisampleStateCreateInfo {
s_type: vk::StructureType::PIPELINE_MULTISAMPLE_STATE_CREATE_INFO,
flags: Default::default(),
p_next: ptr::null(),
rasterization_samples: vk::SampleCountFlags::TYPE_1, rasterization_samples: vk::SampleCountFlags::TYPE_1,
sample_shading_enable: 0, ..Default::default()
min_sample_shading: 0.0,
p_sample_mask: ptr::null(),
alpha_to_one_enable: 0,
alpha_to_coverage_enable: 0,
}; };
let noop_stencil_state = vk::StencilOpState { let noop_stencil_state = vk::StencilOpState {
fail_op: vk::StencilOp::KEEP, fail_op: vk::StencilOp::KEEP,
pass_op: vk::StencilOp::KEEP, pass_op: vk::StencilOp::KEEP,
depth_fail_op: vk::StencilOp::KEEP, depth_fail_op: vk::StencilOp::KEEP,
compare_op: vk::CompareOp::ALWAYS, compare_op: vk::CompareOp::ALWAYS,
compare_mask: 0, ..Default::default()
write_mask: 0,
reference: 0,
}; };
let depth_state_info = vk::PipelineDepthStencilStateCreateInfo { let depth_state_info = vk::PipelineDepthStencilStateCreateInfo {
s_type: vk::StructureType::PIPELINE_DEPTH_STENCIL_STATE_CREATE_INFO,
p_next: ptr::null(),
flags: Default::default(),
depth_test_enable: 1, depth_test_enable: 1,
depth_write_enable: 1, depth_write_enable: 1,
depth_compare_op: vk::CompareOp::LESS_OR_EQUAL, depth_compare_op: vk::CompareOp::LESS_OR_EQUAL,
depth_bounds_test_enable: 0,
stencil_test_enable: 0,
front: noop_stencil_state.clone(), front: noop_stencil_state.clone(),
back: noop_stencil_state.clone(), back: noop_stencil_state.clone(),
max_depth_bounds: 1.0, max_depth_bounds: 1.0,
min_depth_bounds: 0.0, ..Default::default()
}; };
let color_blend_attachment_states = [vk::PipelineColorBlendAttachmentState { let color_blend_attachment_states = [vk::PipelineColorBlendAttachmentState {
blend_enable: 0, blend_enable: 0,
@ -413,48 +331,34 @@ fn main() {
alpha_blend_op: vk::BlendOp::ADD, alpha_blend_op: vk::BlendOp::ADD,
color_write_mask: vk::ColorComponentFlags::all(), color_write_mask: vk::ColorComponentFlags::all(),
}]; }];
let color_blend_state = vk::PipelineColorBlendStateCreateInfo { let color_blend_state = vk::PipelineColorBlendStateCreateInfo::builder()
s_type: vk::StructureType::PIPELINE_COLOR_BLEND_STATE_CREATE_INFO, .logic_op(vk::LogicOp::CLEAR)
p_next: ptr::null(), .attachments(&color_blend_attachment_states);
flags: Default::default(),
logic_op_enable: 0,
logic_op: vk::LogicOp::CLEAR,
attachment_count: color_blend_attachment_states.len() as u32,
p_attachments: color_blend_attachment_states.as_ptr(),
blend_constants: [0.0, 0.0, 0.0, 0.0],
};
let dynamic_state = [vk::DynamicState::VIEWPORT, vk::DynamicState::SCISSOR]; let dynamic_state = [vk::DynamicState::VIEWPORT, vk::DynamicState::SCISSOR];
let dynamic_state_info = vk::PipelineDynamicStateCreateInfo { let dynamic_state_info =
s_type: vk::StructureType::PIPELINE_DYNAMIC_STATE_CREATE_INFO, vk::PipelineDynamicStateCreateInfo::builder().dynamic_states(&dynamic_state);
p_next: ptr::null(),
flags: Default::default(), let graphic_pipeline_info = vk::GraphicsPipelineCreateInfo::builder()
dynamic_state_count: dynamic_state.len() as u32, .stages(&shader_stage_create_infos)
p_dynamic_states: dynamic_state.as_ptr(), .vertex_input_state(&vertex_input_state_info)
}; .input_assembly_state(&vertex_input_assembly_state_info)
let graphic_pipeline_info = vk::GraphicsPipelineCreateInfo { .viewport_state(&viewport_state_info)
s_type: vk::StructureType::GRAPHICS_PIPELINE_CREATE_INFO, .rasterization_state(&rasterization_info)
p_next: ptr::null(), .multisample_state(&multisample_state_info)
flags: vk::PipelineCreateFlags::empty(), .depth_stencil_state(&depth_state_info)
stage_count: shader_stage_create_infos.len() as u32, .color_blend_state(&color_blend_state)
p_stages: shader_stage_create_infos.as_ptr(), .dynamic_state(&dynamic_state_info)
p_vertex_input_state: &vertex_input_state_info, .layout(pipeline_layout)
p_input_assembly_state: &vertex_input_assembly_state_info, .render_pass(renderpass);
p_tessellation_state: ptr::null(),
p_viewport_state: &viewport_state_info,
p_rasterization_state: &rasterization_info,
p_multisample_state: &multisample_state_info,
p_depth_stencil_state: &depth_state_info,
p_color_blend_state: &color_blend_state,
p_dynamic_state: &dynamic_state_info,
layout: pipeline_layout,
render_pass: renderpass,
subpass: 0,
base_pipeline_handle: vk::Pipeline::null(),
base_pipeline_index: 0,
};
let graphics_pipelines = base let graphics_pipelines = base
.device .device
.create_graphics_pipelines(vk::PipelineCache::null(), &[graphic_pipeline_info], None) .create_graphics_pipelines(
vk::PipelineCache::null(),
&[graphic_pipeline_info.build()],
None,
)
.expect("Unable to create graphics pipeline"); .expect("Unable to create graphics pipeline");
let graphic_pipeline = graphics_pipelines[0]; let graphic_pipeline = graphics_pipelines[0];
@ -462,7 +366,7 @@ fn main() {
base.render_loop(|| { base.render_loop(|| {
let (present_index, _) = base let (present_index, _) = base
.swapchain_loader .swapchain_loader
.acquire_next_image_khr( .acquire_next_image(
base.swapchain, base.swapchain,
std::u64::MAX, std::u64::MAX,
base.present_complete_semaphore, base.present_complete_semaphore,
@ -483,18 +387,15 @@ fn main() {
}, },
]; ];
let render_pass_begin_info = vk::RenderPassBeginInfo { let render_pass_begin_info = vk::RenderPassBeginInfo::builder()
s_type: vk::StructureType::RENDER_PASS_BEGIN_INFO, .render_pass(renderpass)
p_next: ptr::null(), .framebuffer(framebuffers[present_index as usize])
render_pass: renderpass, .render_area(vk::Rect2D {
framebuffer: framebuffers[present_index as usize],
render_area: vk::Rect2D {
offset: vk::Offset2D { x: 0, y: 0 }, offset: vk::Offset2D { x: 0, y: 0 },
extent: base.surface_resolution.clone(), extent: base.surface_resolution.clone(),
}, })
clear_value_count: clear_values.len() as u32, .clear_values(&clear_values);
p_clear_values: clear_values.as_ptr(),
};
record_submit_commandbuffer( record_submit_commandbuffer(
&base.device, &base.device,
base.draw_command_buffer, base.draw_command_buffer,
@ -541,18 +442,16 @@ fn main() {
}, },
); );
//let mut present_info_err = mem::uninitialized(); //let mut present_info_err = mem::uninitialized();
let present_info = vk::PresentInfoKHR { let wait_semaphors = [base.rendering_complete_semaphore];
s_type: vk::StructureType::PRESENT_INFO_KHR, let swapchains = [base.swapchain];
p_next: ptr::null(), let image_indices = [present_index];
wait_semaphore_count: 1, let present_info = vk::PresentInfoKHR::builder()
p_wait_semaphores: &base.rendering_complete_semaphore, .wait_semaphores(&wait_semaphors) // &base.rendering_complete_semaphore)
swapchain_count: 1, .swapchains(&swapchains)
p_swapchains: &base.swapchain, .image_indices(&image_indices);
p_image_indices: &present_index,
p_results: ptr::null_mut(),
};
base.swapchain_loader base.swapchain_loader
.queue_present_khr(base.present_queue, &present_info) .queue_present(base.present_queue, &present_info)
.unwrap(); .unwrap();
}); });

View file

@ -2,15 +2,16 @@
extern crate ash; extern crate ash;
#[cfg(target_os = "windows")] #[cfg(target_os = "windows")]
extern crate winapi; extern crate winapi;
extern crate winit; extern crate winit;
#[cfg(target_os = "macos")]
extern crate objc;
#[cfg(target_os = "macos")] #[cfg(target_os = "macos")]
extern crate cocoa; extern crate cocoa;
#[cfg(target_os = "macos")] #[cfg(target_os = "macos")]
extern crate metal_rs as metal; extern crate metal_rs as metal;
#[cfg(target_os = "macos")] #[cfg(target_os = "macos")]
extern crate objc;
#[cfg(target_os = "macos")]
use cocoa::appkit::{NSView, NSWindow}; use cocoa::appkit::{NSView, NSWindow};
#[cfg(target_os = "macos")] #[cfg(target_os = "macos")]
use cocoa::base::id as cocoa_id; use cocoa::base::id as cocoa_id;
@ -21,24 +22,24 @@ use objc::runtime::YES;
#[cfg(target_os = "macos")] #[cfg(target_os = "macos")]
use std::mem; use std::mem;
use ash::vk;
use ash::Device;
use ash::Entry;
use ash::Instance;
pub use ash::version::{DeviceV1_0, EntryV1_0, InstanceV1_0};
use ash::extensions::{DebugReport, Surface, Swapchain};
#[cfg(target_os = "windows")]
use ash::extensions::Win32Surface;
#[cfg(all(unix, not(target_os = "android"), not(target_os = "macos")))] #[cfg(all(unix, not(target_os = "android"), not(target_os = "macos")))]
use ash::extensions::XlibSurface; use ash::extensions::khr::XlibSurface;
use ash::extensions::{
ext::DebugReport,
khr::{Surface, Swapchain},
};
#[cfg(target_os = "windows")]
use ash::extensions::khr::Win32Surface;
#[cfg(target_os = "macos")] #[cfg(target_os = "macos")]
use ash::extensions::MacOSSurface; use ash::extensions::mvk::MacOSSurface;
pub use ash::version::{DeviceV1_0, EntryV1_0, InstanceV1_0};
use ash::{vk, Device, Entry, Instance};
use std::cell::RefCell; use std::cell::RefCell;
use std::default::Default; use std::default::Default;
use std::ffi::{CStr, CString}; use std::ffi::{CStr, CString};
use std::ops::Drop; use std::ops::Drop;
use std::os::raw::{c_char, c_void}; use std::os::raw::{c_char, c_void};
use std::ptr;
// Simple offset_of macro akin to C++ offsetof // Simple offset_of macro akin to C++ offsetof
#[macro_export] #[macro_export]
@ -66,13 +67,12 @@ pub fn record_submit_commandbuffer<D: DeviceV1_0, F: FnOnce(&D, vk::CommandBuffe
.reset_command_buffer( .reset_command_buffer(
command_buffer, command_buffer,
vk::CommandBufferResetFlags::RELEASE_RESOURCES, vk::CommandBufferResetFlags::RELEASE_RESOURCES,
).expect("Reset command buffer failed."); )
let command_buffer_begin_info = vk::CommandBufferBeginInfo { .expect("Reset command buffer failed.");
s_type: vk::StructureType::COMMAND_BUFFER_BEGIN_INFO,
p_next: ptr::null(), let command_buffer_begin_info = vk::CommandBufferBeginInfo::builder()
p_inheritance_info: ptr::null(), .flags(vk::CommandBufferUsageFlags::ONE_TIME_SUBMIT);
flags: vk::CommandBufferUsageFlags::ONE_TIME_SUBMIT,
};
device device
.begin_command_buffer(command_buffer, &command_buffer_begin_info) .begin_command_buffer(command_buffer, &command_buffer_begin_info)
.expect("Begin commandbuffer"); .expect("Begin commandbuffer");
@ -80,27 +80,21 @@ pub fn record_submit_commandbuffer<D: DeviceV1_0, F: FnOnce(&D, vk::CommandBuffe
device device
.end_command_buffer(command_buffer) .end_command_buffer(command_buffer)
.expect("End commandbuffer"); .expect("End commandbuffer");
let fence_create_info = vk::FenceCreateInfo {
s_type: vk::StructureType::FENCE_CREATE_INFO,
p_next: ptr::null(),
flags: vk::FenceCreateFlags::empty(),
};
let submit_fence = device let submit_fence = device
.create_fence(&fence_create_info, None) .create_fence(&vk::FenceCreateInfo::default(), None)
.expect("Create fence failed."); .expect("Create fence failed.");
let submit_info = vk::SubmitInfo {
s_type: vk::StructureType::SUBMIT_INFO, let command_buffers = vec![command_buffer];
p_next: ptr::null(),
wait_semaphore_count: wait_semaphores.len() as u32, let submit_info = vk::SubmitInfo::builder()
p_wait_semaphores: wait_semaphores.as_ptr(), .wait_semaphores(wait_semaphores)
p_wait_dst_stage_mask: wait_mask.as_ptr(), .wait_dst_stage_mask(wait_mask)
command_buffer_count: 1, .command_buffers(&command_buffers)
p_command_buffers: &command_buffer, .signal_semaphores(signal_semaphores);
signal_semaphore_count: signal_semaphores.len() as u32,
p_signal_semaphores: signal_semaphores.as_ptr(),
};
device device
.queue_submit(submit_queue, &[submit_info], submit_fence) .queue_submit(submit_queue, &[submit_info.build()], submit_fence)
.expect("queue submit failed."); .expect("queue submit failed.");
device device
.wait_for_fences(&[submit_fence], true, std::u64::MAX) .wait_for_fences(&[submit_fence], true, std::u64::MAX)
@ -118,16 +112,12 @@ unsafe fn create_surface<E: EntryV1_0, I: InstanceV1_0>(
use winit::os::unix::WindowExt; use winit::os::unix::WindowExt;
let x11_display = window.get_xlib_display().unwrap(); let x11_display = window.get_xlib_display().unwrap();
let x11_window = window.get_xlib_window().unwrap(); let x11_window = window.get_xlib_window().unwrap();
let x11_create_info = vk::XlibSurfaceCreateInfoKHR { let x11_create_info = vk::XlibSurfaceCreateInfoKHR::builder()
s_type: vk::StructureType::XLIB_SURFACE_CREATE_INFO_KHR, .window(x11_window)
p_next: ptr::null(), .dpy(x11_display as *mut vk::Display);
flags: Default::default(),
window: x11_window as vk::Window, let xlib_surface_loader = XlibSurface::new(entry, instance);
dpy: x11_display as *mut vk::Display, xlib_surface_loader.create_xlib_surface(&x11_create_info, None)
};
let xlib_surface_loader =
XlibSurface::new(entry, instance);
xlib_surface_loader.create_xlib_surface_khr(&x11_create_info, None)
} }
#[cfg(target_os = "macos")] #[cfg(target_os = "macos")]
@ -136,6 +126,7 @@ unsafe fn create_surface<E: EntryV1_0, I: InstanceV1_0>(
instance: &I, instance: &I,
window: &winit::Window, window: &winit::Window,
) -> Result<vk::SurfaceKHR, vk::Result> { ) -> Result<vk::SurfaceKHR, vk::Result> {
use std::ptr;
use winit::os::macos::WindowExt; use winit::os::macos::WindowExt;
let wnd: cocoa_id = mem::transmute(window.get_nswindow()); let wnd: cocoa_id = mem::transmute(window.get_nswindow());
@ -153,15 +144,14 @@ unsafe fn create_surface<E: EntryV1_0, I: InstanceV1_0>(
view.setWantsLayer(YES); view.setWantsLayer(YES);
let create_info = vk::MacOSSurfaceCreateInfoMVK { let create_info = vk::MacOSSurfaceCreateInfoMVK {
s_type: vk::StructureType::MacOSSurfaceCreateInfoMvk, s_type: vk::StructureType::MACOS_SURFACE_CREATE_INFO_M,
p_next: ptr::null(), p_next: ptr::null(),
flags: Default::default(), flags: Default::default(),
p_view: window.get_nsview() as *const vk::types::c_void p_view: window.get_nsview() as *const c_void,
}; };
let macos_surface_loader = let macos_surface_loader = MacOSSurface::new(entry, instance);
MacOSSurface::new(entry, instance).expect("Unable to load macOS surface"); macos_surface_loader.create_mac_os_surface_mvk(&create_info, None)
macos_surface_loader.create_macos_surface_mvk(&create_info, None)
} }
#[cfg(target_os = "windows")] #[cfg(target_os = "windows")]
@ -170,6 +160,7 @@ unsafe fn create_surface<E: EntryV1_0, I: InstanceV1_0>(
instance: &I, instance: &I,
window: &winit::Window, window: &winit::Window,
) -> Result<vk::SurfaceKHR, vk::Result> { ) -> Result<vk::SurfaceKHR, vk::Result> {
use std::ptr;
use winapi::shared::windef::HWND; use winapi::shared::windef::HWND;
use winapi::um::libloaderapi::GetModuleHandleW; use winapi::um::libloaderapi::GetModuleHandleW;
use winit::os::windows::WindowExt; use winit::os::windows::WindowExt;
@ -183,9 +174,8 @@ unsafe fn create_surface<E: EntryV1_0, I: InstanceV1_0>(
hinstance: hinstance, hinstance: hinstance,
hwnd: hwnd as *const c_void, hwnd: hwnd as *const c_void,
}; };
let win32_surface_loader = let win32_surface_loader = Win32Surface::new(entry, instance);
Win32Surface::new(entry, instance); win32_surface_loader.create_win32_surface(&win32_create_info, None)
win32_surface_loader.create_win32_surface_khr(&win32_create_info, None)
} }
#[cfg(all(unix, not(target_os = "android"), not(target_os = "macos")))] #[cfg(all(unix, not(target_os = "android"), not(target_os = "macos")))]
@ -332,11 +322,11 @@ impl ExampleBase {
.with_dimensions(winit::dpi::LogicalSize::new( .with_dimensions(winit::dpi::LogicalSize::new(
window_width as f64, window_width as f64,
window_height as f64, window_height as f64,
)).build(&events_loop) ))
.build(&events_loop)
.unwrap(); .unwrap();
let entry = Entry::new().unwrap(); let entry = Entry::new().unwrap();
let app_name = CString::new("VulkanTriangle").unwrap(); let app_name = CString::new("VulkanTriangle").unwrap();
let raw_name = app_name.as_ptr();
let layer_names = [CString::new("VK_LAYER_LUNARG_standard_validation").unwrap()]; let layer_names = [CString::new("VK_LAYER_LUNARG_standard_validation").unwrap()];
let layers_names_raw: Vec<*const i8> = layer_names let layers_names_raw: Vec<*const i8> = layer_names
@ -345,48 +335,40 @@ impl ExampleBase {
.collect(); .collect();
let extension_names_raw = extension_names(); let extension_names_raw = extension_names();
let appinfo = vk::ApplicationInfo {
p_application_name: raw_name, let appinfo = vk::ApplicationInfo::builder()
s_type: vk::StructureType::APPLICATION_INFO, .application_name(&app_name)
p_next: ptr::null(), .application_version(0)
application_version: 0, .engine_name(&app_name)
p_engine_name: raw_name, .engine_version(0)
engine_version: 0, .api_version(vk_make_version!(1, 0, 36));
api_version: vk_make_version!(1, 0, 36),
}; let create_info = vk::InstanceCreateInfo::builder()
let create_info = vk::InstanceCreateInfo { .application_info(&appinfo)
s_type: vk::StructureType::INSTANCE_CREATE_INFO, .enabled_layer_names(&layers_names_raw)
p_next: ptr::null(), .enabled_extension_names(&extension_names_raw);
flags: Default::default(),
p_application_info: &appinfo,
pp_enabled_layer_names: layers_names_raw.as_ptr(),
enabled_layer_count: layers_names_raw.len() as u32,
pp_enabled_extension_names: extension_names_raw.as_ptr(),
enabled_extension_count: extension_names_raw.len() as u32,
};
let instance: Instance = entry let instance: Instance = entry
.create_instance(&create_info, None) .create_instance(&create_info, None)
.expect("Instance creation error"); .expect("Instance creation error");
let debug_info = vk::DebugReportCallbackCreateInfoEXT {
s_type: vk::StructureType::DEBUG_REPORT_CALLBACK_CREATE_INFO_EXT, let debug_info = vk::DebugReportCallbackCreateInfoEXT::builder()
p_next: ptr::null(), .flags(
flags: vk::DebugReportFlagsEXT::ERROR vk::DebugReportFlagsEXT::ERROR
| vk::DebugReportFlagsEXT::WARNING | vk::DebugReportFlagsEXT::WARNING
| vk::DebugReportFlagsEXT::PERFORMANCE_WARNING, | vk::DebugReportFlagsEXT::PERFORMANCE_WARNING,
pfn_callback: Some(vulkan_debug_callback), )
p_user_data: ptr::null_mut(), .pfn_callback(Some(vulkan_debug_callback));
};
let debug_report_loader = let debug_report_loader = DebugReport::new(&entry, &instance);
DebugReport::new(&entry, &instance);
let debug_call_back = debug_report_loader let debug_call_back = debug_report_loader
.create_debug_report_callback_ext(&debug_info, None) .create_debug_report_callback(&debug_info, None)
.unwrap(); .unwrap();
let surface = create_surface(&entry, &instance, &window).unwrap(); let surface = create_surface(&entry, &instance, &window).unwrap();
let pdevices = instance let pdevices = instance
.enumerate_physical_devices() .enumerate_physical_devices()
.expect("Physical device error"); .expect("Physical device error");
let surface_loader = let surface_loader = Surface::new(&entry, &instance);
Surface::new(&entry, &instance);
let (pdevice, queue_family_index) = pdevices let (pdevice, queue_family_index) = pdevices
.iter() .iter()
.map(|pdevice| { .map(|pdevice| {
@ -396,8 +378,8 @@ impl ExampleBase {
.enumerate() .enumerate()
.filter_map(|(index, ref info)| { .filter_map(|(index, ref info)| {
let supports_graphic_and_surface = let supports_graphic_and_surface =
info.queue_flags.contains(vk::QueueFlags::GRAPHICS) && surface_loader info.queue_flags.contains(vk::QueueFlags::GRAPHICS)
.get_physical_device_surface_support_khr( && surface_loader.get_physical_device_surface_support(
*pdevice, *pdevice,
index as u32, index as u32,
surface, surface,
@ -406,8 +388,10 @@ impl ExampleBase {
true => Some((*pdevice, index)), true => Some((*pdevice, index)),
_ => None, _ => None,
} }
}).nth(0) })
}).filter_map(|v| v) .nth(0)
})
.filter_map(|v| v)
.nth(0) .nth(0)
.expect("Couldn't find suitable device."); .expect("Couldn't find suitable device.");
let queue_family_index = queue_family_index as u32; let queue_family_index = queue_family_index as u32;
@ -417,33 +401,24 @@ impl ExampleBase {
..Default::default() ..Default::default()
}; };
let priorities = [1.0]; let priorities = [1.0];
let queue_info = vk::DeviceQueueCreateInfo {
s_type: vk::StructureType::DEVICE_QUEUE_CREATE_INFO, let queue_info = [vk::DeviceQueueCreateInfo::builder()
p_next: ptr::null(), .queue_family_index(queue_family_index)
flags: Default::default(), .queue_priorities(&priorities)
queue_family_index: queue_family_index as u32, .build()];
p_queue_priorities: priorities.as_ptr(),
queue_count: priorities.len() as u32, let device_create_info = vk::DeviceCreateInfo::builder()
}; .queue_create_infos(&queue_info)
let device_create_info = vk::DeviceCreateInfo { .enabled_extension_names(&device_extension_names_raw)
s_type: vk::StructureType::DEVICE_CREATE_INFO, .enabled_features(&features);
p_next: ptr::null(),
flags: Default::default(),
queue_create_info_count: 1,
p_queue_create_infos: &queue_info,
enabled_layer_count: 0,
pp_enabled_layer_names: ptr::null(),
enabled_extension_count: device_extension_names_raw.len() as u32,
pp_enabled_extension_names: device_extension_names_raw.as_ptr(),
p_enabled_features: &features,
};
let device: Device = instance let device: Device = instance
.create_device(pdevice, &device_create_info, None) .create_device(pdevice, &device_create_info, None)
.unwrap(); .unwrap();
let present_queue = device.get_device_queue(queue_family_index as u32, 0); let present_queue = device.get_device_queue(queue_family_index as u32, 0);
let surface_formats = surface_loader let surface_formats = surface_loader
.get_physical_device_surface_formats_khr(pdevice, surface) .get_physical_device_surface_formats(pdevice, surface)
.unwrap(); .unwrap();
let surface_format = surface_formats let surface_format = surface_formats
.iter() .iter()
@ -453,10 +428,11 @@ impl ExampleBase {
color_space: sfmt.color_space, color_space: sfmt.color_space,
}, },
_ => sfmt.clone(), _ => sfmt.clone(),
}).nth(0) })
.nth(0)
.expect("Unable to find suitable surface format."); .expect("Unable to find suitable surface format.");
let surface_capabilities = surface_loader let surface_capabilities = surface_loader
.get_physical_device_surface_capabilities_khr(pdevice, surface) .get_physical_device_surface_capabilities(pdevice, surface)
.unwrap(); .unwrap();
let mut desired_image_count = surface_capabilities.min_image_count + 1; let mut desired_image_count = surface_capabilities.min_image_count + 1;
if surface_capabilities.max_image_count > 0 if surface_capabilities.max_image_count > 0
@ -480,156 +456,135 @@ impl ExampleBase {
surface_capabilities.current_transform surface_capabilities.current_transform
}; };
let present_modes = surface_loader let present_modes = surface_loader
.get_physical_device_surface_present_modes_khr(pdevice, surface) .get_physical_device_surface_present_modes(pdevice, surface)
.unwrap(); .unwrap();
let present_mode = present_modes let present_mode = present_modes
.iter() .iter()
.cloned() .cloned()
.find(|&mode| mode == vk::PresentModeKHR::MAILBOX) .find(|&mode| mode == vk::PresentModeKHR::MAILBOX)
.unwrap_or(vk::PresentModeKHR::FIFO); .unwrap_or(vk::PresentModeKHR::FIFO);
let swapchain_loader = let swapchain_loader = Swapchain::new(&instance, &device);
Swapchain::new(&instance, &device);
let swapchain_create_info = vk::SwapchainCreateInfoKHR { let swapchain_create_info = vk::SwapchainCreateInfoKHR::builder()
s_type: vk::StructureType::SWAPCHAIN_CREATE_INFO_KHR, .surface(surface)
p_next: ptr::null(), .min_image_count(desired_image_count)
flags: Default::default(), .image_color_space(surface_format.color_space)
surface: surface, .image_format(surface_format.format)
min_image_count: desired_image_count, .image_extent(surface_resolution.clone())
image_color_space: surface_format.color_space, .image_usage(vk::ImageUsageFlags::COLOR_ATTACHMENT)
image_format: surface_format.format, .image_sharing_mode(vk::SharingMode::EXCLUSIVE)
image_extent: surface_resolution.clone(), .pre_transform(pre_transform)
image_usage: vk::ImageUsageFlags::COLOR_ATTACHMENT, .composite_alpha(vk::CompositeAlphaFlagsKHR::OPAQUE)
image_sharing_mode: vk::SharingMode::EXCLUSIVE, .present_mode(present_mode)
pre_transform: pre_transform, .clipped(true)
composite_alpha: vk::CompositeAlphaFlagsKHR::OPAQUE, .image_array_layers(1);
present_mode: present_mode,
clipped: 1,
old_swapchain: vk::SwapchainKHR::null(),
image_array_layers: 1,
p_queue_family_indices: ptr::null(),
queue_family_index_count: 0,
};
let swapchain = swapchain_loader let swapchain = swapchain_loader
.create_swapchain_khr(&swapchain_create_info, None) .create_swapchain(&swapchain_create_info, None)
.unwrap(); .unwrap();
let pool_create_info = vk::CommandPoolCreateInfo {
s_type: vk::StructureType::COMMAND_POOL_CREATE_INFO, let pool_create_info = vk::CommandPoolCreateInfo::builder()
p_next: ptr::null(), .flags(vk::CommandPoolCreateFlags::RESET_COMMAND_BUFFER)
flags: vk::CommandPoolCreateFlags::RESET_COMMAND_BUFFER, .queue_family_index(queue_family_index);
queue_family_index: queue_family_index,
};
let pool = device.create_command_pool(&pool_create_info, None).unwrap(); let pool = device.create_command_pool(&pool_create_info, None).unwrap();
let command_buffer_allocate_info = vk::CommandBufferAllocateInfo {
s_type: vk::StructureType::COMMAND_BUFFER_ALLOCATE_INFO, let command_buffer_allocate_info = vk::CommandBufferAllocateInfo::builder()
p_next: ptr::null(), .command_buffer_count(2)
command_buffer_count: 2, .command_pool(pool)
command_pool: pool, .level(vk::CommandBufferLevel::PRIMARY);
level: vk::CommandBufferLevel::PRIMARY,
};
let command_buffers = device let command_buffers = device
.allocate_command_buffers(&command_buffer_allocate_info) .allocate_command_buffers(&command_buffer_allocate_info)
.unwrap(); .unwrap();
let setup_command_buffer = command_buffers[0]; let setup_command_buffer = command_buffers[0];
let draw_command_buffer = command_buffers[1]; let draw_command_buffer = command_buffers[1];
let present_images = swapchain_loader let present_images = swapchain_loader.get_swapchain_images(swapchain).unwrap();
.get_swapchain_images_khr(swapchain)
.unwrap();
let present_image_views: Vec<vk::ImageView> = present_images let present_image_views: Vec<vk::ImageView> = present_images
.iter() .iter()
.map(|&image| { .map(|&image| {
let create_view_info = vk::ImageViewCreateInfo { let create_view_info = vk::ImageViewCreateInfo::builder()
s_type: vk::StructureType::IMAGE_VIEW_CREATE_INFO, .view_type(vk::ImageViewType::TYPE_2D)
p_next: ptr::null(), .format(surface_format.format)
flags: Default::default(), .components(vk::ComponentMapping {
view_type: vk::ImageViewType::TYPE_2D,
format: surface_format.format,
components: vk::ComponentMapping {
r: vk::ComponentSwizzle::R, r: vk::ComponentSwizzle::R,
g: vk::ComponentSwizzle::G, g: vk::ComponentSwizzle::G,
b: vk::ComponentSwizzle::B, b: vk::ComponentSwizzle::B,
a: vk::ComponentSwizzle::A, a: vk::ComponentSwizzle::A,
}, })
subresource_range: vk::ImageSubresourceRange { .subresource_range(vk::ImageSubresourceRange {
aspect_mask: vk::ImageAspectFlags::COLOR, aspect_mask: vk::ImageAspectFlags::COLOR,
base_mip_level: 0, base_mip_level: 0,
level_count: 1, level_count: 1,
base_array_layer: 0, base_array_layer: 0,
layer_count: 1, layer_count: 1,
}, })
image: image, .image(image);
};
device.create_image_view(&create_view_info, None).unwrap() device.create_image_view(&create_view_info, None).unwrap()
}).collect(); })
.collect();
let device_memory_properties = instance.get_physical_device_memory_properties(pdevice); let device_memory_properties = instance.get_physical_device_memory_properties(pdevice);
let depth_image_create_info = vk::ImageCreateInfo { let depth_image_create_info = vk::ImageCreateInfo::builder()
s_type: vk::StructureType::IMAGE_CREATE_INFO, .image_type(vk::ImageType::TYPE_2D)
p_next: ptr::null(), .format(vk::Format::D16_UNORM)
flags: Default::default(), .extent(vk::Extent3D {
image_type: vk::ImageType::TYPE_2D,
format: vk::Format::D16_UNORM,
extent: vk::Extent3D {
width: surface_resolution.width, width: surface_resolution.width,
height: surface_resolution.height, height: surface_resolution.height,
depth: 1, depth: 1,
}, })
mip_levels: 1, .mip_levels(1)
array_layers: 1, .array_layers(1)
samples: vk::SampleCountFlags::TYPE_1, .samples(vk::SampleCountFlags::TYPE_1)
tiling: vk::ImageTiling::OPTIMAL, .tiling(vk::ImageTiling::OPTIMAL)
usage: vk::ImageUsageFlags::DEPTH_STENCIL_ATTACHMENT, .usage(vk::ImageUsageFlags::DEPTH_STENCIL_ATTACHMENT)
sharing_mode: vk::SharingMode::EXCLUSIVE, .sharing_mode(vk::SharingMode::EXCLUSIVE);
queue_family_index_count: 0,
p_queue_family_indices: ptr::null(),
initial_layout: vk::ImageLayout::UNDEFINED,
};
let depth_image = device.create_image(&depth_image_create_info, None).unwrap(); let depth_image = device.create_image(&depth_image_create_info, None).unwrap();
let depth_image_memory_req = device.get_image_memory_requirements(depth_image); let depth_image_memory_req = device.get_image_memory_requirements(depth_image);
let depth_image_memory_index = find_memorytype_index( let depth_image_memory_index = find_memorytype_index(
&depth_image_memory_req, &depth_image_memory_req,
&device_memory_properties, &device_memory_properties,
vk::MemoryPropertyFlags::DEVICE_LOCAL, vk::MemoryPropertyFlags::DEVICE_LOCAL,
).expect("Unable to find suitable memory index for depth image."); )
.expect("Unable to find suitable memory index for depth image.");
let depth_image_allocate_info = vk::MemoryAllocateInfo::builder()
.allocation_size(depth_image_memory_req.size)
.memory_type_index(depth_image_memory_index);
let depth_image_allocate_info = vk::MemoryAllocateInfo {
s_type: vk::StructureType::MEMORY_ALLOCATE_INFO,
p_next: ptr::null(),
allocation_size: depth_image_memory_req.size,
memory_type_index: depth_image_memory_index,
};
let depth_image_memory = device let depth_image_memory = device
.allocate_memory(&depth_image_allocate_info, None) .allocate_memory(&depth_image_allocate_info, None)
.unwrap(); .unwrap();
device device
.bind_image_memory(depth_image, depth_image_memory, 0) .bind_image_memory(depth_image, depth_image_memory, 0)
.expect("Unable to bind depth image memory"); .expect("Unable to bind depth image memory");
record_submit_commandbuffer( record_submit_commandbuffer(
&device, &device,
setup_command_buffer, setup_command_buffer,
present_queue, present_queue,
&[vk::PipelineStageFlags::BOTTOM_OF_PIPE], &[],
&[], &[],
&[], &[],
|device, setup_command_buffer| { |device, setup_command_buffer| {
let layout_transition_barrier = vk::ImageMemoryBarrier { let layout_transition_barriers = vk::ImageMemoryBarrier::builder()
s_type: vk::StructureType::IMAGE_MEMORY_BARRIER, .image(depth_image)
p_next: ptr::null(), .dst_access_mask(
src_access_mask: Default::default(), vk::AccessFlags::DEPTH_STENCIL_ATTACHMENT_READ
dst_access_mask: vk::AccessFlags::DEPTH_STENCIL_ATTACHMENT_READ | vk::AccessFlags::DEPTH_STENCIL_ATTACHMENT_WRITE,
| vk::AccessFlags::DEPTH_STENCIL_ATTACHMENT_WRITE, )
old_layout: vk::ImageLayout::UNDEFINED, .new_layout(vk::ImageLayout::DEPTH_STENCIL_ATTACHMENT_OPTIMAL)
new_layout: vk::ImageLayout::DEPTH_STENCIL_ATTACHMENT_OPTIMAL, .old_layout(vk::ImageLayout::UNDEFINED)
src_queue_family_index: vk::QUEUE_FAMILY_IGNORED, .subresource_range(
dst_queue_family_index: vk::QUEUE_FAMILY_IGNORED, vk::ImageSubresourceRange::builder()
image: depth_image, .aspect_mask(vk::ImageAspectFlags::DEPTH)
subresource_range: vk::ImageSubresourceRange { .layer_count(1)
aspect_mask: vk::ImageAspectFlags::DEPTH, .level_count(1)
base_mip_level: 0, .build(),
level_count: 1, );
base_array_layer: 0,
layer_count: 1,
},
};
device.cmd_pipeline_barrier( device.cmd_pipeline_barrier(
setup_command_buffer, setup_command_buffer,
vk::PipelineStageFlags::BOTTOM_OF_PIPE, vk::PipelineStageFlags::BOTTOM_OF_PIPE,
@ -637,39 +592,29 @@ impl ExampleBase {
vk::DependencyFlags::empty(), vk::DependencyFlags::empty(),
&[], &[],
&[], &[],
&[layout_transition_barrier], &[layout_transition_barriers.build()],
); );
}, },
); );
let depth_image_view_info = vk::ImageViewCreateInfo {
s_type: vk::StructureType::IMAGE_VIEW_CREATE_INFO, let depth_image_view_info = vk::ImageViewCreateInfo::builder()
p_next: ptr::null(), .subresource_range(
flags: Default::default(), vk::ImageSubresourceRange::builder()
view_type: vk::ImageViewType::TYPE_2D, .aspect_mask(vk::ImageAspectFlags::DEPTH)
format: depth_image_create_info.format, .level_count(1)
components: vk::ComponentMapping { .layer_count(1)
r: vk::ComponentSwizzle::IDENTITY, .build(),
g: vk::ComponentSwizzle::IDENTITY, )
b: vk::ComponentSwizzle::IDENTITY, .image(depth_image)
a: vk::ComponentSwizzle::IDENTITY, .format(depth_image_create_info.format)
}, .view_type(vk::ImageViewType::TYPE_2D);
subresource_range: vk::ImageSubresourceRange {
aspect_mask: vk::ImageAspectFlags::DEPTH,
base_mip_level: 0,
level_count: 1,
base_array_layer: 0,
layer_count: 1,
},
image: depth_image,
};
let depth_image_view = device let depth_image_view = device
.create_image_view(&depth_image_view_info, None) .create_image_view(&depth_image_view_info, None)
.unwrap(); .unwrap();
let semaphore_create_info = vk::SemaphoreCreateInfo {
s_type: vk::StructureType::SEMAPHORE_CREATE_INFO, let semaphore_create_info = vk::SemaphoreCreateInfo::default();
p_next: ptr::null(),
flags: Default::default(),
};
let present_complete_semaphore = device let present_complete_semaphore = device
.create_semaphore(&semaphore_create_info, None) .create_semaphore(&semaphore_create_info, None)
.unwrap(); .unwrap();
@ -725,11 +670,11 @@ impl Drop for ExampleBase {
} }
self.device.destroy_command_pool(self.pool, None); self.device.destroy_command_pool(self.pool, None);
self.swapchain_loader self.swapchain_loader
.destroy_swapchain_khr(self.swapchain, None); .destroy_swapchain(self.swapchain, None);
self.device.destroy_device(None); self.device.destroy_device(None);
self.surface_loader.destroy_surface_khr(self.surface, None); self.surface_loader.destroy_surface(self.surface, None);
self.debug_report_loader self.debug_report_loader
.destroy_debug_report_callback_ext(self.debug_call_back, None); .destroy_debug_report_callback(self.debug_call_back, None);
self.instance.destroy_instance(None); self.instance.destroy_instance(None);
} }
} }

View file

@ -4,7 +4,7 @@ version = "0.1.0"
authors = ["Maik Klein <maikklein@googlemail.com>"] authors = ["Maik Klein <maikklein@googlemail.com>"]
[dependencies] [dependencies]
vk-parse = "0.1" vk-parse = "0.2"
vkxml = "0.3" vkxml = "0.3"
nom = "4.0" nom = "4.0"
heck = "0.3" heck = "0.3"

@ -1 +1 @@
Subproject commit 718a04e51b967fbe6de9d09ecfc15397f0eae5bd Subproject commit 114c3546e195819bd53a34b39f5194b2989a5b12

File diff suppressed because it is too large Load diff

17
imdone-help.md Normal file
View file

@ -0,0 +1,17 @@
imdone-help
====
#HELP: Try dragging this card to your new list id:8 +imdone-help
#HELP: Ignore files by adding `.imdoneignore` to the root of your project. id:1 +imdone-help
- [imdone.io](https://imdone.io) implements this with the [ignore package](https://www.npmjs.com/package/ignore)
#HELP: Use markdown in todo comments or in the description id:3 +imdone-help
- **This is a description...**
#HELP: Add tags to your comments like this `+mvp` id:5 +imdone-help
#HELP: Add metadata like this... points:5 id:7 +imdone-help
- [imdone.io](https://imdone.io) adds `id:n` to all your todo comments, so take care to leave that one alone
#HELP: Include subtasks using GFM task lists id:9 +imdone-help
- [ ] A task yet to be done
- [x] This is done

View file

@ -1,2 +1 @@
max_width = 100 max_width = 100
error_on_line_overflow = false