mirror of
https://github.com/KhronosGroup/Vulkan-Hpp.git
synced 2024-10-14 16:32:17 +00:00
Add samples DynamicUniform, EnableValidationWithCallback, EnumerateDevicesAdvanced, Events (#313)
+ slightly adjust some other samples.
This commit is contained in:
parent
bcc02a1cb0
commit
f7ec6041b3
@ -37,7 +37,6 @@ int main(int /*argc*/, char ** /*argv*/)
|
|||||||
|
|
||||||
std::vector<vk::PhysicalDevice> physicalDevices = instance->enumeratePhysicalDevices();
|
std::vector<vk::PhysicalDevice> physicalDevices = instance->enumeratePhysicalDevices();
|
||||||
assert(!physicalDevices.empty());
|
assert(!physicalDevices.empty());
|
||||||
vk::PhysicalDeviceMemoryProperties memoryProperties = physicalDevices[0].getMemoryProperties();
|
|
||||||
|
|
||||||
vk::su::SurfaceData surfaceData(instance, AppName, AppName, vk::Extent2D(500, 500));
|
vk::su::SurfaceData surfaceData(instance, AppName, AppName, vk::Extent2D(500, 500));
|
||||||
|
|
||||||
|
@ -37,7 +37,6 @@ int main(int /*argc*/, char ** /*argv*/)
|
|||||||
|
|
||||||
std::vector<vk::PhysicalDevice> physicalDevices = instance->enumeratePhysicalDevices();
|
std::vector<vk::PhysicalDevice> physicalDevices = instance->enumeratePhysicalDevices();
|
||||||
assert(!physicalDevices.empty());
|
assert(!physicalDevices.empty());
|
||||||
vk::PhysicalDeviceMemoryProperties memoryProperties = physicalDevices[0].getMemoryProperties();
|
|
||||||
|
|
||||||
vk::su::SurfaceData surfaceData(instance, AppName, AppName, vk::Extent2D(500, 500));
|
vk::su::SurfaceData surfaceData(instance, AppName, AppName, vk::Extent2D(500, 500));
|
||||||
|
|
||||||
@ -77,7 +76,7 @@ int main(int /*argc*/, char ** /*argv*/)
|
|||||||
std::vector<vk::UniqueDescriptorSet> descriptorSets = device->allocateDescriptorSetsUnique(vk::DescriptorSetAllocateInfo(descriptorPool.get(), 1, &descriptorSetLayout.get()));
|
std::vector<vk::UniqueDescriptorSet> descriptorSets = device->allocateDescriptorSetsUnique(vk::DescriptorSetAllocateInfo(descriptorPool.get(), 1, &descriptorSetLayout.get()));
|
||||||
|
|
||||||
vk::DescriptorBufferInfo descriptorBufferInfo(uniformBufferData.buffer.get(), 0, sizeof(glm::mat4x4));
|
vk::DescriptorBufferInfo descriptorBufferInfo(uniformBufferData.buffer.get(), 0, sizeof(glm::mat4x4));
|
||||||
vk::su::updateDescriptorSets(device, descriptorSets[0], &descriptorBufferInfo);
|
vk::su::updateDescriptorSets(device, descriptorSets[0], vk::DescriptorType::eUniformBuffer, &descriptorBufferInfo);
|
||||||
|
|
||||||
vk::UniquePipelineCache pipelineCache = device->createPipelineCacheUnique(vk::PipelineCacheCreateInfo());
|
vk::UniquePipelineCache pipelineCache = device->createPipelineCacheUnique(vk::PipelineCacheCreateInfo());
|
||||||
vk::UniquePipeline graphicsPipeline = vk::su::createGraphicsPipeline(device, pipelineCache, vertexShaderModule, fragmentShaderModule, sizeof(coloredCubeData[0]), pipelineLayout, renderPass);
|
vk::UniquePipeline graphicsPipeline = vk::su::createGraphicsPipeline(device, pipelineCache, vertexShaderModule, fragmentShaderModule, sizeof(coloredCubeData[0]), pipelineLayout, renderPass);
|
||||||
|
@ -134,7 +134,6 @@ int main(int /*argc*/, char ** /*argv*/)
|
|||||||
|
|
||||||
std::vector<vk::PhysicalDevice> physicalDevices = instance->enumeratePhysicalDevices();
|
std::vector<vk::PhysicalDevice> physicalDevices = instance->enumeratePhysicalDevices();
|
||||||
assert(!physicalDevices.empty());
|
assert(!physicalDevices.empty());
|
||||||
vk::PhysicalDeviceMemoryProperties memoryProperties = physicalDevices[0].getMemoryProperties();
|
|
||||||
|
|
||||||
vk::su::SurfaceData surfaceData(instance, AppName, AppName, vk::Extent2D(500, 500));
|
vk::su::SurfaceData surfaceData(instance, AppName, AppName, vk::Extent2D(500, 500));
|
||||||
|
|
||||||
@ -160,7 +159,7 @@ int main(int /*argc*/, char ** /*argv*/)
|
|||||||
vk::su::BufferData uniformBufferData(physicalDevices[0], device, sizeof(glm::mat4x4), vk::BufferUsageFlagBits::eUniformBuffer);
|
vk::su::BufferData uniformBufferData(physicalDevices[0], device, sizeof(glm::mat4x4), vk::BufferUsageFlagBits::eUniformBuffer);
|
||||||
vk::su::copyToDevice(device, uniformBufferData.deviceMemory, vk::su::createModelViewProjectionClipMatrix());
|
vk::su::copyToDevice(device, uniformBufferData.deviceMemory, vk::su::createModelViewProjectionClipMatrix());
|
||||||
|
|
||||||
vk::UniqueDescriptorSetLayout descriptorSetLayout = vk::su::createDescriptorSetLayout(device, textured);
|
vk::UniqueDescriptorSetLayout descriptorSetLayout = vk::su::createDescriptorSetLayout(device, vk::DescriptorType::eUniformBuffer, textured);
|
||||||
vk::UniquePipelineLayout pipelineLayout = device->createPipelineLayoutUnique(vk::PipelineLayoutCreateInfo(vk::PipelineLayoutCreateFlags(), 1, &descriptorSetLayout.get()));
|
vk::UniquePipelineLayout pipelineLayout = device->createPipelineLayoutUnique(vk::PipelineLayoutCreateInfo(vk::PipelineLayoutCreateFlags(), 1, &descriptorSetLayout.get()));
|
||||||
|
|
||||||
vk::UniqueRenderPass renderPass = vk::su::createRenderPass(device, vk::su::pickColorFormat(physicalDevices[0].getSurfaceFormatsKHR(surfaceData.surface.get())), depthBufferData.format);
|
vk::UniqueRenderPass renderPass = vk::su::createRenderPass(device, vk::su::pickColorFormat(physicalDevices[0].getSurfaceFormatsKHR(surfaceData.surface.get())), depthBufferData.format);
|
||||||
@ -175,12 +174,12 @@ int main(int /*argc*/, char ** /*argv*/)
|
|||||||
vk::su::BufferData vertexBufferData(physicalDevices[0], device, sizeof(texturedCubeData), vk::BufferUsageFlagBits::eVertexBuffer);
|
vk::su::BufferData vertexBufferData(physicalDevices[0], device, sizeof(texturedCubeData), vk::BufferUsageFlagBits::eVertexBuffer);
|
||||||
vk::su::copyToDevice(device, vertexBufferData.deviceMemory, texturedCubeData, sizeof(texturedCubeData) / sizeof(texturedCubeData[0]));
|
vk::su::copyToDevice(device, vertexBufferData.deviceMemory, texturedCubeData, sizeof(texturedCubeData) / sizeof(texturedCubeData[0]));
|
||||||
|
|
||||||
vk::UniqueDescriptorPool descriptorPool = vk::su::createDescriptorPool(device, textured);
|
vk::UniqueDescriptorPool descriptorPool = vk::su::createDescriptorPool(device, vk::DescriptorType::eUniformBuffer, textured);
|
||||||
std::vector<vk::UniqueDescriptorSet> descriptorSets = device->allocateDescriptorSetsUnique(vk::DescriptorSetAllocateInfo(descriptorPool.get(), 1, &descriptorSetLayout.get()));
|
std::vector<vk::UniqueDescriptorSet> descriptorSets = device->allocateDescriptorSetsUnique(vk::DescriptorSetAllocateInfo(descriptorPool.get(), 1, &descriptorSetLayout.get()));
|
||||||
|
|
||||||
vk::DescriptorBufferInfo bufferInfo(uniformBufferData.buffer.get(), 0, sizeof(glm::mat4x4));
|
vk::DescriptorBufferInfo bufferInfo(uniformBufferData.buffer.get(), 0, sizeof(glm::mat4x4));
|
||||||
vk::DescriptorImageInfo imageInfo(textureData.textureSampler.get(), textureData.imageData->imageView.get(), vk::ImageLayout::eShaderReadOnlyOptimal);
|
vk::DescriptorImageInfo imageInfo(textureData.textureSampler.get(), textureData.imageData->imageView.get(), vk::ImageLayout::eShaderReadOnlyOptimal);
|
||||||
vk::su::updateDescriptorSets(device, descriptorSets[0], &bufferInfo, &imageInfo);
|
vk::su::updateDescriptorSets(device, descriptorSets[0], vk::DescriptorType::eUniformBuffer, &bufferInfo, &imageInfo);
|
||||||
|
|
||||||
vk::UniquePipelineCache pipelineCache = device->createPipelineCacheUnique(vk::PipelineCacheCreateInfo());
|
vk::UniquePipelineCache pipelineCache = device->createPipelineCacheUnique(vk::PipelineCacheCreateInfo());
|
||||||
vk::UniquePipeline graphicsPipeline = vk::su::createGraphicsPipeline(device, pipelineCache, vertexShaderModule, fragmentShaderModule, sizeof(texturedCubeData[0]), pipelineLayout, renderPass);
|
vk::UniquePipeline graphicsPipeline = vk::su::createGraphicsPipeline(device, pipelineCache, vertexShaderModule, fragmentShaderModule, sizeof(texturedCubeData[0]), pipelineLayout, renderPass);
|
||||||
|
44
samples/DynamicUniform/CMakeLists.txt
Normal file
44
samples/DynamicUniform/CMakeLists.txt
Normal file
@ -0,0 +1,44 @@
|
|||||||
|
# Copyright(c) 2019, NVIDIA CORPORATION. All rights reserved.
|
||||||
|
#
|
||||||
|
# Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
# you may not use this file except in compliance with the License.
|
||||||
|
# You may obtain a copy of the License at
|
||||||
|
#
|
||||||
|
# http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
#
|
||||||
|
# Unless required by applicable law or agreed to in writing, software
|
||||||
|
# distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
# See the License for the specific language governing permissions and
|
||||||
|
# limitations under the License.
|
||||||
|
|
||||||
|
cmake_minimum_required(VERSION 3.2)
|
||||||
|
|
||||||
|
project(DynamicUniform)
|
||||||
|
|
||||||
|
set(HEADERS
|
||||||
|
../utils/geometries.hpp
|
||||||
|
../utils/math.hpp
|
||||||
|
../utils/shaders.hpp
|
||||||
|
../utils/utils.hpp
|
||||||
|
)
|
||||||
|
|
||||||
|
set(SOURCES
|
||||||
|
DynamicUniform.cpp
|
||||||
|
../utils/math.cpp
|
||||||
|
../utils/shaders.cpp
|
||||||
|
../utils/utils.cpp
|
||||||
|
)
|
||||||
|
|
||||||
|
source_group(headers FILES ${HEADERS})
|
||||||
|
source_group(sources FILES ${SOURCES})
|
||||||
|
|
||||||
|
add_executable(DynamicUniform
|
||||||
|
${HEADERS}
|
||||||
|
${SOURCES}
|
||||||
|
)
|
||||||
|
|
||||||
|
set_target_properties(DynamicUniform PROPERTIES FOLDER "Samples")
|
||||||
|
target_include_directories(DynamicUniform PUBLIC ${CMAKE_SOURCE_DIR}/glslang)
|
||||||
|
target_link_libraries(DynamicUniform PUBLIC glslang SPIRV "$ENV{VULKAN_SDK}/Lib/vulkan-1.lib"
|
||||||
|
)
|
186
samples/DynamicUniform/DynamicUniform.cpp
Normal file
186
samples/DynamicUniform/DynamicUniform.cpp
Normal file
@ -0,0 +1,186 @@
|
|||||||
|
// Copyright(c) 2019, NVIDIA CORPORATION. All rights reserved.
|
||||||
|
//
|
||||||
|
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
// you may not use this file except in compliance with the License.
|
||||||
|
// You may obtain a copy of the License at
|
||||||
|
//
|
||||||
|
// http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
//
|
||||||
|
// Unless required by applicable law or agreed to in writing, software
|
||||||
|
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
// See the License for the specific language governing permissions and
|
||||||
|
// limitations under the License.
|
||||||
|
//
|
||||||
|
// VulkanHpp Samples : DynamicUniform
|
||||||
|
// Draw 2 Cubes using dynamic uniform buffer
|
||||||
|
|
||||||
|
#include "../utils/geometries.hpp"
|
||||||
|
#include "../utils/math.hpp"
|
||||||
|
#include "../utils/shaders.hpp"
|
||||||
|
#include "../utils/utils.hpp"
|
||||||
|
#include "vulkan/vulkan.hpp"
|
||||||
|
#include "SPIRV/GlslangToSpv.h"
|
||||||
|
#include <iostream>
|
||||||
|
|
||||||
|
static char const* AppName = "DynamicUniform";
|
||||||
|
static char const* EngineName = "Vulkan.hpp";
|
||||||
|
|
||||||
|
int main(int /*argc*/, char ** /*argv*/)
|
||||||
|
{
|
||||||
|
try
|
||||||
|
{
|
||||||
|
vk::UniqueInstance instance = vk::su::createInstance(AppName, EngineName, vk::su::getInstanceExtensions());
|
||||||
|
#if !defined(NDEBUG)
|
||||||
|
vk::UniqueDebugReportCallbackEXT debugReportCallback = vk::su::createDebugReportCallback(instance);
|
||||||
|
#endif
|
||||||
|
|
||||||
|
std::vector<vk::PhysicalDevice> physicalDevices = instance->enumeratePhysicalDevices();
|
||||||
|
assert(!physicalDevices.empty());
|
||||||
|
|
||||||
|
vk::su::SurfaceData surfaceData(instance, AppName, AppName, vk::Extent2D(500, 500));
|
||||||
|
|
||||||
|
std::pair<uint32_t, uint32_t> graphicsAndPresentQueueFamilyIndex = vk::su::findGraphicsAndPresentQueueFamilyIndex(physicalDevices[0], surfaceData.surface);
|
||||||
|
vk::UniqueDevice device = vk::su::createDevice(physicalDevices[0], graphicsAndPresentQueueFamilyIndex.first, vk::su::getDeviceExtensions());
|
||||||
|
|
||||||
|
vk::UniqueCommandPool commandPool = vk::su::createCommandPool(device, graphicsAndPresentQueueFamilyIndex.first);
|
||||||
|
std::vector<vk::UniqueCommandBuffer> commandBuffers = device->allocateCommandBuffersUnique(vk::CommandBufferAllocateInfo(commandPool.get(), vk::CommandBufferLevel::ePrimary, 1));
|
||||||
|
|
||||||
|
vk::Queue graphicsQueue = device->getQueue(graphicsAndPresentQueueFamilyIndex.first, 0);
|
||||||
|
vk::Queue presentQueue = device->getQueue(graphicsAndPresentQueueFamilyIndex.second, 0);
|
||||||
|
|
||||||
|
vk::su::SwapChainData swapChainData(physicalDevices[0], device, surfaceData.surface, surfaceData.extent, vk::ImageUsageFlagBits::eColorAttachment | vk::ImageUsageFlagBits::eTransferSrc
|
||||||
|
, graphicsAndPresentQueueFamilyIndex.first, graphicsAndPresentQueueFamilyIndex.second);
|
||||||
|
|
||||||
|
vk::su::DepthBufferData depthBufferData(physicalDevices[0], device, vk::Format::eD16Unorm, surfaceData.extent);
|
||||||
|
|
||||||
|
vk::UniqueRenderPass renderPass = vk::su::createRenderPass(device, vk::su::pickColorFormat(physicalDevices[0].getSurfaceFormatsKHR(surfaceData.surface.get())), depthBufferData.format);
|
||||||
|
|
||||||
|
glslang::InitializeProcess();
|
||||||
|
vk::UniqueShaderModule vertexShaderModule = vk::su::createShaderModule(device, vk::ShaderStageFlagBits::eVertex, vertexShaderText_PC_C);
|
||||||
|
vk::UniqueShaderModule fragmentShaderModule = vk::su::createShaderModule(device, vk::ShaderStageFlagBits::eFragment, fragmentShaderText_C_C);
|
||||||
|
glslang::FinalizeProcess();
|
||||||
|
|
||||||
|
std::vector<vk::UniqueFramebuffer> framebuffers = vk::su::createFramebuffers(device, renderPass, swapChainData.imageViews, depthBufferData.imageView, surfaceData.extent);
|
||||||
|
|
||||||
|
vk::su::BufferData vertexBufferData(physicalDevices[0], device, sizeof(coloredCubeData), vk::BufferUsageFlagBits::eVertexBuffer);
|
||||||
|
vk::su::copyToDevice(device, vertexBufferData.deviceMemory, coloredCubeData, sizeof(coloredCubeData) / sizeof(coloredCubeData[0]));
|
||||||
|
|
||||||
|
/* VULKAN_KEY_START */
|
||||||
|
|
||||||
|
vk::PhysicalDeviceLimits limits = physicalDevices[0].getProperties().limits;
|
||||||
|
if (limits.maxDescriptorSetUniformBuffersDynamic < 1)
|
||||||
|
{
|
||||||
|
std::cout << "No dynamic uniform buffers supported\n";
|
||||||
|
exit(-1);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Set up uniform buffer with 2 transform matrices in it */
|
||||||
|
glm::mat4x4 mvpcs[2];
|
||||||
|
glm::mat4x4 model = glm::mat4x4(1.0f);
|
||||||
|
glm::mat4x4 view = glm::lookAt(glm::vec3(0.0f, 3.0f, -10.0f), glm::vec3(0.0f, 0.0f, 0.0f), glm::vec3(0.0f, -1.0f, 0.0f));
|
||||||
|
glm::mat4x4 projection = glm::perspective(glm::radians(45.0f), 1.0f, 0.1f, 100.0f);
|
||||||
|
glm::mat4x4 clip = glm::mat4x4(1.0f, 0.0f, 0.0f, 0.0f, 0.0f, -1.0f, 0.0f, 0.0f, 0.0f, 0.0f, 0.5f, 0.0f, 0.0f, 0.0f, 0.5f, 1.0f); // vulkan clip space has inverted y and half z !
|
||||||
|
mvpcs[0] = clip * projection * view * model;
|
||||||
|
|
||||||
|
model = glm::translate(model, glm::vec3(-1.5f, -1.5f, -1.5f));
|
||||||
|
mvpcs[1] = clip * projection * view * model;
|
||||||
|
|
||||||
|
VkDeviceSize bufferSize = sizeof(glm::mat4x4);
|
||||||
|
if (limits.minUniformBufferOffsetAlignment)
|
||||||
|
{
|
||||||
|
bufferSize = (bufferSize + limits.minUniformBufferOffsetAlignment - 1) & ~(limits.minUniformBufferOffsetAlignment - 1);
|
||||||
|
}
|
||||||
|
|
||||||
|
vk::su::BufferData uniformBufferData(physicalDevices[0], device, 2 * bufferSize, vk::BufferUsageFlagBits::eUniformBuffer);
|
||||||
|
vk::su::copyToDevice(device, uniformBufferData.deviceMemory, mvpcs, 2, bufferSize);
|
||||||
|
|
||||||
|
// create a DescriptorSetLayout with vk::DescriptorType::eUniformBufferDynamic
|
||||||
|
vk::UniqueDescriptorSetLayout descriptorSetLayout = vk::su::createDescriptorSetLayout(device, vk::DescriptorType::eUniformBufferDynamic);
|
||||||
|
vk::UniquePipelineLayout pipelineLayout = device->createPipelineLayoutUnique(vk::PipelineLayoutCreateInfo(vk::PipelineLayoutCreateFlags(), 1, &descriptorSetLayout.get()));
|
||||||
|
|
||||||
|
// create a DescriptorPool with vk::DescriptorType::eUniformBufferDynamic
|
||||||
|
vk::UniqueDescriptorPool descriptorPool = vk::su::createDescriptorPool(device, vk::DescriptorType::eUniformBufferDynamic);
|
||||||
|
std::vector<vk::UniqueDescriptorSet> descriptorSets = device->allocateDescriptorSetsUnique(vk::DescriptorSetAllocateInfo(descriptorPool.get(), 1, &descriptorSetLayout.get()));
|
||||||
|
|
||||||
|
vk::DescriptorBufferInfo descriptorBufferInfo(uniformBufferData.buffer.get(), 0, sizeof(glm::mat4x4));
|
||||||
|
vk::su::updateDescriptorSets(device, descriptorSets[0], vk::DescriptorType::eUniformBufferDynamic, &descriptorBufferInfo);
|
||||||
|
|
||||||
|
vk::UniquePipelineCache pipelineCache = device->createPipelineCacheUnique(vk::PipelineCacheCreateInfo());
|
||||||
|
vk::UniquePipeline graphicsPipeline = vk::su::createGraphicsPipeline(device, pipelineCache, vertexShaderModule, fragmentShaderModule, sizeof(coloredCubeData[0]), pipelineLayout, renderPass);
|
||||||
|
|
||||||
|
// Get the index of the next available swapchain image:
|
||||||
|
vk::UniqueSemaphore imageAcquiredSemaphore = device->createSemaphoreUnique(vk::SemaphoreCreateInfo());
|
||||||
|
vk::ResultValue<uint32_t> currentBuffer = device->acquireNextImageKHR(swapChainData.swapChain.get(), vk::su::FenceTimeout, imageAcquiredSemaphore.get(), nullptr);
|
||||||
|
assert(currentBuffer.result == vk::Result::eSuccess);
|
||||||
|
assert(currentBuffer.value < framebuffers.size());
|
||||||
|
|
||||||
|
commandBuffers[0]->begin(vk::CommandBufferBeginInfo(vk::CommandBufferUsageFlags()));
|
||||||
|
|
||||||
|
vk::ClearValue clearValues[2];
|
||||||
|
clearValues[0].color = vk::ClearColorValue(std::array<float, 4>({ 0.2f, 0.2f, 0.2f, 0.2f }));
|
||||||
|
clearValues[1].depthStencil = vk::ClearDepthStencilValue(1.0f, 0);
|
||||||
|
vk::RenderPassBeginInfo renderPassBeginInfo(renderPass.get(), framebuffers[currentBuffer.value].get(), vk::Rect2D(vk::Offset2D(0, 0), surfaceData.extent), 2, clearValues);
|
||||||
|
commandBuffers[0]->beginRenderPass(renderPassBeginInfo, vk::SubpassContents::eInline);
|
||||||
|
commandBuffers[0]->bindPipeline(vk::PipelineBindPoint::eGraphics, graphicsPipeline.get());
|
||||||
|
|
||||||
|
vk::Viewport viewport(0.0f, 0.0f, static_cast<float>(surfaceData.extent.width), static_cast<float>(surfaceData.extent.height), 0.0f, 1.0f);
|
||||||
|
commandBuffers[0]->setViewport(0, viewport);
|
||||||
|
|
||||||
|
vk::Rect2D scissor(vk::Offset2D(0, 0), surfaceData.extent);
|
||||||
|
commandBuffers[0]->setScissor(0, scissor);
|
||||||
|
|
||||||
|
/* The first draw should use the first matrix in the buffer */
|
||||||
|
uint32_t dynamicOffset = 0;
|
||||||
|
commandBuffers[0]->bindDescriptorSets(vk::PipelineBindPoint::eGraphics, pipelineLayout.get(), 0, descriptorSets[0].get(), dynamicOffset);
|
||||||
|
|
||||||
|
vk::DeviceSize vertexOffset = 0;
|
||||||
|
commandBuffers[0]->bindVertexBuffers(0, vertexBufferData.buffer.get(), vertexOffset);
|
||||||
|
commandBuffers[0]->draw(12 * 3, 1, 0, 0);
|
||||||
|
|
||||||
|
// the second draw should use the second matrix in the buffer;
|
||||||
|
dynamicOffset = (uint32_t)bufferSize;
|
||||||
|
commandBuffers[0]->bindDescriptorSets(vk::PipelineBindPoint::eGraphics, pipelineLayout.get(), 0, descriptorSets[0].get(), dynamicOffset);
|
||||||
|
commandBuffers[0]->draw(12 * 3, 1, 0, 0);
|
||||||
|
|
||||||
|
commandBuffers[0]->endRenderPass();
|
||||||
|
commandBuffers[0]->end();
|
||||||
|
|
||||||
|
vk::UniqueFence drawFence = device->createFenceUnique(vk::FenceCreateInfo());
|
||||||
|
|
||||||
|
vk::PipelineStageFlags waitDestinationStageMask(vk::PipelineStageFlagBits::eColorAttachmentOutput);
|
||||||
|
vk::SubmitInfo submitInfo(1, &imageAcquiredSemaphore.get(), &waitDestinationStageMask, 1, &commandBuffers[0].get());
|
||||||
|
graphicsQueue.submit(submitInfo, drawFence.get());
|
||||||
|
|
||||||
|
while (vk::Result::eTimeout == device->waitForFences(drawFence.get(), VK_TRUE, vk::su::FenceTimeout))
|
||||||
|
;
|
||||||
|
|
||||||
|
presentQueue.presentKHR(vk::PresentInfoKHR(0, nullptr, 1, &swapChainData.swapChain.get(), ¤tBuffer.value));
|
||||||
|
Sleep(1000);
|
||||||
|
|
||||||
|
/* VULKAN_KEY_END */
|
||||||
|
|
||||||
|
device->waitIdle();
|
||||||
|
#if defined(VK_USE_PLATFORM_WIN32_KHR)
|
||||||
|
DestroyWindow(surfaceData.window);
|
||||||
|
#else
|
||||||
|
#pragma error "unhandled platform"
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
catch (vk::SystemError err)
|
||||||
|
{
|
||||||
|
std::cout << "vk::SystemError: " << err.what() << std::endl;
|
||||||
|
exit(-1);
|
||||||
|
}
|
||||||
|
catch (std::runtime_error err)
|
||||||
|
{
|
||||||
|
std::cout << "std::runtime_error: " << err.what() << std::endl;
|
||||||
|
exit(-1);
|
||||||
|
}
|
||||||
|
catch (...)
|
||||||
|
{
|
||||||
|
std::cout << "unknown error\n";
|
||||||
|
exit(-1);
|
||||||
|
}
|
||||||
|
return 0;
|
||||||
|
}
|
37
samples/EnableValidationWithCallback/CMakeLists.txt
Normal file
37
samples/EnableValidationWithCallback/CMakeLists.txt
Normal file
@ -0,0 +1,37 @@
|
|||||||
|
# Copyright(c) 2019, NVIDIA CORPORATION. All rights reserved.
|
||||||
|
#
|
||||||
|
# Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
# you may not use this file except in compliance with the License.
|
||||||
|
# You may obtain a copy of the License at
|
||||||
|
#
|
||||||
|
# http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
#
|
||||||
|
# Unless required by applicable law or agreed to in writing, software
|
||||||
|
# distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
# See the License for the specific language governing permissions and
|
||||||
|
# limitations under the License.
|
||||||
|
|
||||||
|
cmake_minimum_required(VERSION 3.2)
|
||||||
|
|
||||||
|
project(EnableValidationWithCallback)
|
||||||
|
|
||||||
|
set(HEADERS
|
||||||
|
)
|
||||||
|
|
||||||
|
set(SOURCES
|
||||||
|
EnableValidationWithCallback.cpp
|
||||||
|
)
|
||||||
|
|
||||||
|
source_group(headers FILES ${HEADERS})
|
||||||
|
source_group(sources FILES ${SOURCES})
|
||||||
|
|
||||||
|
add_executable(EnableValidationWithCallback
|
||||||
|
${HEADERS}
|
||||||
|
${SOURCES}
|
||||||
|
)
|
||||||
|
|
||||||
|
set_target_properties(EnableValidationWithCallback PROPERTIES FOLDER "Samples")
|
||||||
|
target_include_directories(EnableValidationWithCallback PUBLIC ${CMAKE_SOURCE_DIR}/glslang)
|
||||||
|
target_link_libraries(EnableValidationWithCallback PUBLIC glslang SPIRV "$ENV{VULKAN_SDK}/Lib/vulkan-1.lib"
|
||||||
|
)
|
@ -0,0 +1,178 @@
|
|||||||
|
// Copyright(c) 2019, NVIDIA CORPORATION. All rights reserved.
|
||||||
|
//
|
||||||
|
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
// you may not use this file except in compliance with the License.
|
||||||
|
// You may obtain a copy of the License at
|
||||||
|
//
|
||||||
|
// http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
//
|
||||||
|
// Unless required by applicable law or agreed to in writing, software
|
||||||
|
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
// See the License for the specific language governing permissions and
|
||||||
|
// limitations under the License.
|
||||||
|
//
|
||||||
|
// VulkanHpp Samples : EnableValidationWithCallback
|
||||||
|
// Show how to enable validation layers and provide callback
|
||||||
|
|
||||||
|
#include "../utils/utils.hpp"
|
||||||
|
#include "vulkan/vulkan.hpp"
|
||||||
|
#include <algorithm>
|
||||||
|
#include <iostream>
|
||||||
|
#include <sstream>
|
||||||
|
|
||||||
|
static char const* AppName = "EnableValidationWithCallback";
|
||||||
|
static char const* EngineName = "Vulkan.hpp";
|
||||||
|
|
||||||
|
PFN_vkCreateDebugReportCallbackEXT pfnVkCreateDebugReportCallbackEXT;
|
||||||
|
PFN_vkDestroyDebugReportCallbackEXT pfnVkDestroyDebugReportCallbackEXT;
|
||||||
|
|
||||||
|
VKAPI_ATTR VkResult VKAPI_CALL vkCreateDebugReportCallbackEXT(VkInstance instance, const VkDebugReportCallbackCreateInfoEXT* pCreateInfo, const VkAllocationCallbacks* pAllocator, VkDebugReportCallbackEXT* pCallback)
|
||||||
|
{
|
||||||
|
return pfnVkCreateDebugReportCallbackEXT(instance, pCreateInfo, pAllocator, pCallback);
|
||||||
|
}
|
||||||
|
|
||||||
|
VKAPI_ATTR void VKAPI_CALL vkDestroyDebugReportCallbackEXT(VkInstance instance, VkDebugReportCallbackEXT callback, const VkAllocationCallbacks* pAllocator)
|
||||||
|
{
|
||||||
|
pfnVkDestroyDebugReportCallbackEXT(instance, callback, pAllocator);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
VKAPI_ATTR VkBool32 VKAPI_CALL dbgFunc(VkDebugReportFlagsEXT flags, VkDebugReportObjectTypeEXT /*objType*/, uint64_t /*srcObject*/, size_t /*location*/, int32_t msgCode, const char *pLayerPrefix, const char *pMsg, void * /*pUserData*/)
|
||||||
|
{
|
||||||
|
std::ostringstream message;
|
||||||
|
|
||||||
|
switch (flags)
|
||||||
|
{
|
||||||
|
case VK_DEBUG_REPORT_INFORMATION_BIT_EXT:
|
||||||
|
message << "INFORMATION: ";
|
||||||
|
break;
|
||||||
|
case VK_DEBUG_REPORT_WARNING_BIT_EXT:
|
||||||
|
message << "WARNING: ";
|
||||||
|
break;
|
||||||
|
case VK_DEBUG_REPORT_PERFORMANCE_WARNING_BIT_EXT:
|
||||||
|
message << "PERFORMANCE WARNING: ";
|
||||||
|
break;
|
||||||
|
case VK_DEBUG_REPORT_ERROR_BIT_EXT:
|
||||||
|
message << "ERROR: ";
|
||||||
|
break;
|
||||||
|
case VK_DEBUG_REPORT_DEBUG_BIT_EXT:
|
||||||
|
message << "DEBUG: ";
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
message << "unknown flag (" << flags << "): ";
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
message << "[" << pLayerPrefix << "] Code " << msgCode << " : " << pMsg;
|
||||||
|
|
||||||
|
#ifdef _WIN32
|
||||||
|
MessageBox(NULL, message.str().c_str(), "Alert", MB_OK);
|
||||||
|
#else
|
||||||
|
std::cout << message.str() << std::endl;
|
||||||
|
#endif
|
||||||
|
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool checkLayers(std::vector<char const*> const& layers, std::vector<vk::LayerProperties> const& properties)
|
||||||
|
{
|
||||||
|
// return true if all layers are listed in the properties
|
||||||
|
return std::all_of(layers.begin(), layers.end(), [&properties](char const* name)
|
||||||
|
{
|
||||||
|
return std::find_if(properties.begin(), properties.end(), [&name](vk::LayerProperties const& property) { return strcmp(property.layerName, name) == 0; }) != properties.end();
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
int main(int /*argc*/, char ** /*argv*/)
|
||||||
|
{
|
||||||
|
try
|
||||||
|
{
|
||||||
|
std::vector<vk::LayerProperties> instanceLayerProperties = vk::enumerateInstanceLayerProperties();
|
||||||
|
|
||||||
|
/* VULKAN_KEY_START */
|
||||||
|
|
||||||
|
// Use standard_validation meta layer that enables all recommended validation layers
|
||||||
|
std::vector<char const*> instanceLayerNames;
|
||||||
|
instanceLayerNames.push_back("VK_LAYER_LUNARG_standard_validation");
|
||||||
|
if (!checkLayers(instanceLayerNames, instanceLayerProperties))
|
||||||
|
{
|
||||||
|
// If standard validation is not present, search instead for the individual layers that make it up, in the correct order.
|
||||||
|
instanceLayerNames.clear();
|
||||||
|
instanceLayerNames.push_back("VK_LAYER_GOOGLE_threading");
|
||||||
|
instanceLayerNames.push_back("VK_LAYER_LUNARG_parameter_validation");
|
||||||
|
instanceLayerNames.push_back("VK_LAYER_LUNARG_object_tracker");
|
||||||
|
instanceLayerNames.push_back("VK_LAYER_LUNARG_core_validation");
|
||||||
|
instanceLayerNames.push_back("VK_LAYER_GOOGLE_unique_objects");
|
||||||
|
|
||||||
|
if (!checkLayers(instanceLayerNames, instanceLayerProperties))
|
||||||
|
{
|
||||||
|
std::cout << "Set the environment variable VK_LAYER_PATH to point to the location of your layers" << std::endl;
|
||||||
|
exit(1);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Enable debug callback extension */
|
||||||
|
std::vector<char const*> instanceExtensionNames;
|
||||||
|
instanceExtensionNames.push_back(VK_EXT_DEBUG_REPORT_EXTENSION_NAME);
|
||||||
|
|
||||||
|
vk::ApplicationInfo applicationInfo(AppName, 1, EngineName, 1, VK_API_VERSION_1_0);
|
||||||
|
vk::InstanceCreateInfo instanceCreateInfo( vk::InstanceCreateFlags(), &applicationInfo, vk::su::checked_cast<uint32_t>(instanceLayerNames.size()), instanceLayerNames.data(),
|
||||||
|
vk::su::checked_cast<uint32_t>(instanceExtensionNames.size()) , instanceExtensionNames.data() );
|
||||||
|
vk::UniqueInstance instance = vk::createInstanceUnique(instanceCreateInfo);
|
||||||
|
|
||||||
|
std::vector<vk::PhysicalDevice> physicalDevices = instance->enumeratePhysicalDevices();
|
||||||
|
assert(!physicalDevices.empty());
|
||||||
|
|
||||||
|
std::vector<vk::QueueFamilyProperties> queueFamilyProperties = physicalDevices[0].getQueueFamilyProperties();
|
||||||
|
assert(!queueFamilyProperties.empty());
|
||||||
|
|
||||||
|
auto qfpIt = std::find_if(queueFamilyProperties.begin(), queueFamilyProperties.end(), [](vk::QueueFamilyProperties const& qfp) { return !!(qfp.queueFlags & vk::QueueFlagBits::eGraphics); });
|
||||||
|
assert(qfpIt != queueFamilyProperties.end());
|
||||||
|
uint32_t queueFamilyIndex = static_cast<uint32_t>(std::distance(queueFamilyProperties.begin(), qfpIt));
|
||||||
|
|
||||||
|
float queuePriority = 0.0f;
|
||||||
|
vk::DeviceQueueCreateInfo deviceQueueCreateInfo(vk::DeviceQueueCreateFlags(), queueFamilyIndex, 1, &queuePriority);
|
||||||
|
vk::UniqueDevice device = physicalDevices[0].createDeviceUnique(vk::DeviceCreateInfo(vk::DeviceCreateFlags(), 1, &deviceQueueCreateInfo));
|
||||||
|
|
||||||
|
pfnVkCreateDebugReportCallbackEXT = reinterpret_cast<PFN_vkCreateDebugReportCallbackEXT>(instance->getProcAddr("vkCreateDebugReportCallbackEXT"));
|
||||||
|
if (!pfnVkCreateDebugReportCallbackEXT)
|
||||||
|
{
|
||||||
|
std::cout << "GetInstanceProcAddr: Unable to find vkCreateDebugReportCallbackEXT function." << std::endl;
|
||||||
|
exit(1);
|
||||||
|
}
|
||||||
|
pfnVkDestroyDebugReportCallbackEXT = reinterpret_cast<PFN_vkDestroyDebugReportCallbackEXT>(instance->getProcAddr("vkDestroyDebugReportCallbackEXT"));
|
||||||
|
if (!pfnVkDestroyDebugReportCallbackEXT)
|
||||||
|
{
|
||||||
|
std::cout << "GetInstanceProcAddr: Unable to find vkDestroyDebugReportCallbackEXT function." << std::endl;
|
||||||
|
exit(1);
|
||||||
|
}
|
||||||
|
|
||||||
|
vk::UniqueDebugReportCallbackEXT debugReportCallback = instance->createDebugReportCallbackEXTUnique(vk::DebugReportCallbackCreateInfoEXT(vk::DebugReportFlagBitsEXT::eError | vk::DebugReportFlagBitsEXT::eWarning, dbgFunc));
|
||||||
|
|
||||||
|
// Create a command pool (not a UniqueCommandPool, for testing purposes!
|
||||||
|
vk::CommandPool commandPool = device->createCommandPool(vk::CommandPoolCreateInfo(vk::CommandPoolCreateFlags(), queueFamilyIndex));
|
||||||
|
|
||||||
|
// The commandPool is not destroyed automatically (as it's not a UniqueCommandPool.
|
||||||
|
// That is, the device is destroyed before the commmand pool and will trigger a validation error.
|
||||||
|
std::cout << "*** INTENTIONALLY calling vkDestroyDevice before destroying command pool ***\n";
|
||||||
|
std::cout << "*** The following error message is EXPECTED ***\n";
|
||||||
|
|
||||||
|
/* VULKAN_KEY_END */
|
||||||
|
}
|
||||||
|
catch (vk::SystemError err)
|
||||||
|
{
|
||||||
|
std::cout << "vk::SystemError: " << err.what() << std::endl;
|
||||||
|
exit(-1);
|
||||||
|
}
|
||||||
|
catch (std::runtime_error err)
|
||||||
|
{
|
||||||
|
std::cout << "std::runtime_error: " << err.what() << std::endl;
|
||||||
|
exit(-1);
|
||||||
|
}
|
||||||
|
catch (...)
|
||||||
|
{
|
||||||
|
std::cout << "unknown error\n";
|
||||||
|
exit(-1);
|
||||||
|
}
|
||||||
|
return 0;
|
||||||
|
}
|
37
samples/EnumerateDevicesAdvanced/CMakeLists.txt
Normal file
37
samples/EnumerateDevicesAdvanced/CMakeLists.txt
Normal file
@ -0,0 +1,37 @@
|
|||||||
|
# Copyright(c) 2018-2019, NVIDIA CORPORATION. All rights reserved.
|
||||||
|
#
|
||||||
|
# Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
# you may not use this file except in compliance with the License.
|
||||||
|
# You may obtain a copy of the License at
|
||||||
|
#
|
||||||
|
# http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
#
|
||||||
|
# Unless required by applicable law or agreed to in writing, software
|
||||||
|
# distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
# See the License for the specific language governing permissions and
|
||||||
|
# limitations under the License.
|
||||||
|
|
||||||
|
cmake_minimum_required(VERSION 3.2)
|
||||||
|
|
||||||
|
project(EnumerateDevicesAdvanced)
|
||||||
|
|
||||||
|
set(HEADERS
|
||||||
|
../utils/utils.hpp
|
||||||
|
)
|
||||||
|
|
||||||
|
set(SOURCES
|
||||||
|
EnumerateDevicesAdvanced.cpp
|
||||||
|
../utils/utils.cpp
|
||||||
|
)
|
||||||
|
|
||||||
|
source_group(headers FILES ${HEADERS})
|
||||||
|
source_group(sources FILES ${SOURCES})
|
||||||
|
|
||||||
|
add_executable(EnumerateDevicesAdvanced
|
||||||
|
${HEADERS}
|
||||||
|
${SOURCES}
|
||||||
|
)
|
||||||
|
|
||||||
|
set_target_properties(EnumerateDevicesAdvanced PROPERTIES FOLDER "Samples")
|
||||||
|
target_link_libraries(EnumerateDevicesAdvanced "$ENV{VULKAN_SDK}/Lib/vulkan-1.lib")
|
@ -0,0 +1,94 @@
|
|||||||
|
// Copyright(c) 2018-2019, NVIDIA CORPORATION. All rights reserved.
|
||||||
|
//
|
||||||
|
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
// you may not use this file except in compliance with the License.
|
||||||
|
// You may obtain a copy of the License at
|
||||||
|
//
|
||||||
|
// http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
//
|
||||||
|
// Unless required by applicable law or agreed to in writing, software
|
||||||
|
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
// See the License for the specific language governing permissions and
|
||||||
|
// limitations under the License.
|
||||||
|
//
|
||||||
|
// VulkanHpp Samples : EnumerateDevicesAdvanced
|
||||||
|
// Enumerate physical devices
|
||||||
|
|
||||||
|
#include "../utils/utils.hpp"
|
||||||
|
#include "vulkan/vulkan.hpp"
|
||||||
|
#include <iomanip>
|
||||||
|
#include <iostream>
|
||||||
|
|
||||||
|
static char const* AppName = "EnumerateDevicesAdvanced";
|
||||||
|
static char const* EngineName = "Vulkan.hpp";
|
||||||
|
|
||||||
|
void print_UUID(uint8_t *pipelineCacheUUID)
|
||||||
|
{
|
||||||
|
for (int j = 0; j < VK_UUID_SIZE; ++j)
|
||||||
|
{
|
||||||
|
std::cout << std::setw(2) << (uint32_t)pipelineCacheUUID[j];
|
||||||
|
if (j == 3 || j == 5 || j == 7 || j == 9)
|
||||||
|
{
|
||||||
|
std::cout << '-';
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
int main(int /*argc*/, char ** /*argv*/)
|
||||||
|
{
|
||||||
|
try
|
||||||
|
{
|
||||||
|
vk::UniqueInstance instance = vk::su::createInstance(AppName, EngineName);
|
||||||
|
#if !defined(NDEBUG)
|
||||||
|
vk::UniqueDebugReportCallbackEXT debugReportCallback = vk::su::createDebugReportCallback(instance);
|
||||||
|
#endif
|
||||||
|
|
||||||
|
/* VULKAN_HPP_KEY_START */
|
||||||
|
|
||||||
|
// enumerate the physicalDevices
|
||||||
|
std::vector<vk::PhysicalDevice> physicalDevices = instance->enumeratePhysicalDevices();
|
||||||
|
|
||||||
|
for (auto const& physicalDevice : physicalDevices)
|
||||||
|
{
|
||||||
|
vk::PhysicalDeviceProperties properties = physicalDevice.getProperties();
|
||||||
|
|
||||||
|
std::cout << "apiVersion: ";
|
||||||
|
std::cout << ((properties.apiVersion >> 22) & 0xfff) << '.'; // Major.
|
||||||
|
std::cout << ((properties.apiVersion >> 12) & 0x3ff) << '.'; // Minor.
|
||||||
|
std::cout << (properties.apiVersion & 0xfff); // Patch.
|
||||||
|
std::cout << '\n';
|
||||||
|
|
||||||
|
std::cout << "driverVersion: " << properties.driverVersion << '\n';
|
||||||
|
|
||||||
|
std::cout << std::showbase << std::internal << std::setfill('0') << std::hex;
|
||||||
|
std::cout << "vendorId: " << std::setw(6) << properties.vendorID << '\n';
|
||||||
|
std::cout << "deviceId: " << std::setw(6) << properties.deviceID << '\n';
|
||||||
|
std::cout << std::noshowbase << std::right << std::setfill(' ') << std::dec;
|
||||||
|
|
||||||
|
std::cout << "deviceType: " << vk::to_string(properties.deviceType) << "\n";
|
||||||
|
|
||||||
|
std::cout << "deviceName: " << properties.deviceName << '\n';
|
||||||
|
|
||||||
|
std::cout << "pipelineCacheUUID: ";
|
||||||
|
std::cout << std::setfill('0') << std::hex;
|
||||||
|
print_UUID(properties.pipelineCacheUUID);
|
||||||
|
std::cout << std::setfill(' ') << std::dec;
|
||||||
|
std::cout << '\n';
|
||||||
|
std::cout << '\n';
|
||||||
|
}
|
||||||
|
|
||||||
|
/* VULKAN_HPP_KEY_END */
|
||||||
|
}
|
||||||
|
catch (vk::SystemError err)
|
||||||
|
{
|
||||||
|
std::cout << "vk::SystemError: " << err.what() << std::endl;
|
||||||
|
exit(-1);
|
||||||
|
}
|
||||||
|
catch (...)
|
||||||
|
{
|
||||||
|
std::cout << "unknown error\n";
|
||||||
|
exit(-1);
|
||||||
|
}
|
||||||
|
return 0;
|
||||||
|
}
|
44
samples/Events/CMakeLists.txt
Normal file
44
samples/Events/CMakeLists.txt
Normal file
@ -0,0 +1,44 @@
|
|||||||
|
# Copyright(c) 2019, NVIDIA CORPORATION. All rights reserved.
|
||||||
|
#
|
||||||
|
# Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
# you may not use this file except in compliance with the License.
|
||||||
|
# You may obtain a copy of the License at
|
||||||
|
#
|
||||||
|
# http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
#
|
||||||
|
# Unless required by applicable law or agreed to in writing, software
|
||||||
|
# distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
# See the License for the specific language governing permissions and
|
||||||
|
# limitations under the License.
|
||||||
|
|
||||||
|
cmake_minimum_required(VERSION 3.2)
|
||||||
|
|
||||||
|
project(Events)
|
||||||
|
|
||||||
|
set(HEADERS
|
||||||
|
../utils/geometries.hpp
|
||||||
|
../utils/math.hpp
|
||||||
|
../utils/shaders.hpp
|
||||||
|
../utils/utils.hpp
|
||||||
|
)
|
||||||
|
|
||||||
|
set(SOURCES
|
||||||
|
Events.cpp
|
||||||
|
../utils/math.cpp
|
||||||
|
../utils/shaders.cpp
|
||||||
|
../utils/utils.cpp
|
||||||
|
)
|
||||||
|
|
||||||
|
source_group(headers FILES ${HEADERS})
|
||||||
|
source_group(sources FILES ${SOURCES})
|
||||||
|
|
||||||
|
add_executable(Events
|
||||||
|
${HEADERS}
|
||||||
|
${SOURCES}
|
||||||
|
)
|
||||||
|
|
||||||
|
set_target_properties(Events PROPERTIES FOLDER "Samples")
|
||||||
|
target_include_directories(Events PUBLIC ${CMAKE_SOURCE_DIR}/glslang)
|
||||||
|
target_link_libraries(Events PUBLIC glslang SPIRV "$ENV{VULKAN_SDK}/Lib/vulkan-1.lib"
|
||||||
|
)
|
156
samples/Events/Events.cpp
Normal file
156
samples/Events/Events.cpp
Normal file
@ -0,0 +1,156 @@
|
|||||||
|
// Copyright(c) 2019, NVIDIA CORPORATION. All rights reserved.
|
||||||
|
//
|
||||||
|
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
// you may not use this file except in compliance with the License.
|
||||||
|
// You may obtain a copy of the License at
|
||||||
|
//
|
||||||
|
// http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
//
|
||||||
|
// Unless required by applicable law or agreed to in writing, software
|
||||||
|
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
// See the License for the specific language governing permissions and
|
||||||
|
// limitations under the License.
|
||||||
|
//
|
||||||
|
// VulkanHpp Samples : Events
|
||||||
|
// Use basic events
|
||||||
|
|
||||||
|
#include "../utils/geometries.hpp"
|
||||||
|
#include "../utils/math.hpp"
|
||||||
|
#include "../utils/shaders.hpp"
|
||||||
|
#include "../utils/utils.hpp"
|
||||||
|
#include "vulkan/vulkan.hpp"
|
||||||
|
#include "SPIRV/GlslangToSpv.h"
|
||||||
|
#include <iostream>
|
||||||
|
|
||||||
|
static char const* AppName = "Events";
|
||||||
|
static char const* EngineName = "Vulkan.hpp";
|
||||||
|
|
||||||
|
int main(int /*argc*/, char ** /*argv*/)
|
||||||
|
{
|
||||||
|
try
|
||||||
|
{
|
||||||
|
vk::UniqueInstance instance = vk::su::createInstance(AppName, EngineName, vk::su::getInstanceExtensions());
|
||||||
|
#if !defined(NDEBUG)
|
||||||
|
vk::UniqueDebugReportCallbackEXT debugReportCallback = vk::su::createDebugReportCallback(instance);
|
||||||
|
#endif
|
||||||
|
|
||||||
|
std::vector<vk::PhysicalDevice> physicalDevices = instance->enumeratePhysicalDevices();
|
||||||
|
assert(!physicalDevices.empty());
|
||||||
|
|
||||||
|
uint32_t graphicsQueueFamilyIndex = vk::su::findGraphicsQueueFamilyIndex(physicalDevices[0].getQueueFamilyProperties());
|
||||||
|
vk::UniqueDevice device = vk::su::createDevice(physicalDevices[0], graphicsQueueFamilyIndex);
|
||||||
|
|
||||||
|
vk::UniqueCommandPool commandPool = vk::su::createCommandPool(device, graphicsQueueFamilyIndex);
|
||||||
|
std::vector<vk::UniqueCommandBuffer> commandBuffers = device->allocateCommandBuffersUnique(vk::CommandBufferAllocateInfo(commandPool.get(), vk::CommandBufferLevel::ePrimary, 1));
|
||||||
|
|
||||||
|
vk::Queue graphicsQueue = device->getQueue(graphicsQueueFamilyIndex, 0);
|
||||||
|
|
||||||
|
/* VULKAN_KEY_START */
|
||||||
|
|
||||||
|
// Start with a trivial command buffer and make sure fence wait doesn't time out
|
||||||
|
commandBuffers[0]->begin(vk::CommandBufferBeginInfo(vk::CommandBufferUsageFlags()));
|
||||||
|
commandBuffers[0]->setViewport(0, vk::Viewport(0.0f, 0.0f, 10.0f, 10.0f, 0.0f, 1.0f));
|
||||||
|
commandBuffers[0]->end();
|
||||||
|
|
||||||
|
vk::UniqueFence fence = device->createFenceUnique(vk::FenceCreateInfo());
|
||||||
|
|
||||||
|
vk::PipelineStageFlags waitDestinationStageMask(vk::PipelineStageFlagBits::eColorAttachmentOutput);
|
||||||
|
vk::SubmitInfo submitInfo(0, nullptr, &waitDestinationStageMask, 1, &commandBuffers[0].get());
|
||||||
|
graphicsQueue.submit(submitInfo, fence.get());
|
||||||
|
|
||||||
|
// Make sure timeout is long enough for a simple command buffer without waiting for an event
|
||||||
|
vk::Result result;
|
||||||
|
int timeouts = -1;
|
||||||
|
do
|
||||||
|
{
|
||||||
|
result = device->waitForFences(fence.get(), true, vk::su::FenceTimeout);
|
||||||
|
timeouts++;
|
||||||
|
} while (result == vk::Result::eTimeout);
|
||||||
|
assert(result == vk::Result::eSuccess);
|
||||||
|
if (timeouts != 0)
|
||||||
|
{
|
||||||
|
std::cout << "Unsuitable timeout value, exiting\n";
|
||||||
|
exit(-1);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Now create an event and wait for it on the GPU
|
||||||
|
vk::UniqueEvent event = device->createEventUnique(vk::EventCreateInfo(vk::EventCreateFlags()));
|
||||||
|
|
||||||
|
commandBuffers[0]->reset(vk::CommandBufferResetFlags());
|
||||||
|
commandBuffers[0]->begin(vk::CommandBufferBeginInfo());
|
||||||
|
commandBuffers[0]->waitEvents(event.get(), vk::PipelineStageFlagBits::eHost, vk::PipelineStageFlagBits::eBottomOfPipe, nullptr, nullptr, nullptr);
|
||||||
|
commandBuffers[0]->end();
|
||||||
|
device->resetFences(fence.get());
|
||||||
|
|
||||||
|
// Note that stepping through this code in the debugger is a bad idea because the GPU can TDR waiting for the event.
|
||||||
|
// Execute the code from vkQueueSubmit through vkSetEvent without breakpoints
|
||||||
|
waitDestinationStageMask = vk::PipelineStageFlagBits::eBottomOfPipe;
|
||||||
|
graphicsQueue.submit(submitInfo, fence.get());
|
||||||
|
|
||||||
|
// We should timeout waiting for the fence because the GPU should be waiting on the event
|
||||||
|
result = device->waitForFences(fence.get(), true, vk::su::FenceTimeout);
|
||||||
|
if (result != vk::Result::eTimeout)
|
||||||
|
{
|
||||||
|
std::cout << "Didn't get expected timeout in vkWaitForFences, exiting\n";
|
||||||
|
exit(-1);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Set the event from the CPU and wait for the fence.
|
||||||
|
// This should succeed since we set the event
|
||||||
|
device->setEvent(event.get());
|
||||||
|
do
|
||||||
|
{
|
||||||
|
result = device->waitForFences(fence.get(), true, vk::su::FenceTimeout);
|
||||||
|
} while (result == vk::Result::eTimeout);
|
||||||
|
assert(result == vk::Result::eSuccess);
|
||||||
|
|
||||||
|
commandBuffers[0]->reset({});
|
||||||
|
device->resetFences(fence.get());
|
||||||
|
device->resetEvent(event.get());
|
||||||
|
|
||||||
|
// Now set the event from the GPU and wait on the CPU
|
||||||
|
commandBuffers[0]->begin(vk::CommandBufferBeginInfo());
|
||||||
|
commandBuffers[0]->setEvent(event.get(), vk::PipelineStageFlagBits::eBottomOfPipe);
|
||||||
|
commandBuffers[0]->end();
|
||||||
|
|
||||||
|
// Look for the event on the CPU. It should be RESET since we haven't sent the command buffer yet.
|
||||||
|
result = device->getEventStatus(event.get());
|
||||||
|
assert(result == vk::Result::eEventReset);
|
||||||
|
|
||||||
|
// Send the command buffer and loop waiting for the event
|
||||||
|
graphicsQueue.submit(submitInfo, fence.get());
|
||||||
|
|
||||||
|
int polls = 0;
|
||||||
|
do
|
||||||
|
{
|
||||||
|
result = device->getEventStatus(event.get());
|
||||||
|
polls++;
|
||||||
|
} while (result != vk::Result::eEventSet);
|
||||||
|
printf("%d polls to find the event set\n", polls);
|
||||||
|
|
||||||
|
do
|
||||||
|
{
|
||||||
|
result = device->waitForFences(fence.get(), true, vk::su::FenceTimeout);
|
||||||
|
} while (result == vk::Result::eTimeout);
|
||||||
|
assert(result == vk::Result::eSuccess);
|
||||||
|
|
||||||
|
/* VULKAN_KEY_END */
|
||||||
|
}
|
||||||
|
catch (vk::SystemError err)
|
||||||
|
{
|
||||||
|
std::cout << "vk::SystemError: " << err.what() << std::endl;
|
||||||
|
exit(-1);
|
||||||
|
}
|
||||||
|
catch (std::runtime_error err)
|
||||||
|
{
|
||||||
|
std::cout << "std::runtime_error: " << err.what() << std::endl;
|
||||||
|
exit(-1);
|
||||||
|
}
|
||||||
|
catch (...)
|
||||||
|
{
|
||||||
|
std::cout << "unknown error\n";
|
||||||
|
exit(-1);
|
||||||
|
}
|
||||||
|
return 0;
|
||||||
|
}
|
@ -66,10 +66,10 @@ namespace vk
|
|||||||
return instance->createDebugReportCallbackEXTUnique(vk::DebugReportCallbackCreateInfoEXT(flags, &vk::su::debugReportCallback));
|
return instance->createDebugReportCallbackEXTUnique(vk::DebugReportCallbackCreateInfoEXT(flags, &vk::su::debugReportCallback));
|
||||||
}
|
}
|
||||||
|
|
||||||
vk::UniqueDescriptorPool createDescriptorPool(vk::UniqueDevice &device, bool textured)
|
vk::UniqueDescriptorPool createDescriptorPool(vk::UniqueDevice &device, vk::DescriptorType descriptorType, bool textured)
|
||||||
{
|
{
|
||||||
std::vector<vk::DescriptorPoolSize> poolSizes;
|
std::vector<vk::DescriptorPoolSize> poolSizes;
|
||||||
poolSizes.push_back(vk::DescriptorPoolSize(vk::DescriptorType::eUniformBuffer, 1));
|
poolSizes.push_back(vk::DescriptorPoolSize(descriptorType, 1));
|
||||||
if (textured)
|
if (textured)
|
||||||
{
|
{
|
||||||
poolSizes.push_back(vk::DescriptorPoolSize(vk::DescriptorType::eCombinedImageSampler, 1));
|
poolSizes.push_back(vk::DescriptorPoolSize(vk::DescriptorType::eCombinedImageSampler, 1));
|
||||||
@ -78,10 +78,10 @@ namespace vk
|
|||||||
return device->createDescriptorPoolUnique(descriptorPoolCreateInfo);
|
return device->createDescriptorPoolUnique(descriptorPoolCreateInfo);
|
||||||
}
|
}
|
||||||
|
|
||||||
vk::UniqueDescriptorSetLayout createDescriptorSetLayout(vk::UniqueDevice &device, bool textured)
|
vk::UniqueDescriptorSetLayout createDescriptorSetLayout(vk::UniqueDevice &device, vk::DescriptorType descriptorType, bool textured)
|
||||||
{
|
{
|
||||||
std::vector<vk::DescriptorSetLayoutBinding> bindings;
|
std::vector<vk::DescriptorSetLayoutBinding> bindings;
|
||||||
bindings.push_back(vk::DescriptorSetLayoutBinding(0, vk::DescriptorType::eUniformBuffer, 1, vk::ShaderStageFlagBits::eVertex));
|
bindings.push_back(vk::DescriptorSetLayoutBinding(0, descriptorType, 1, vk::ShaderStageFlagBits::eVertex));
|
||||||
if (textured)
|
if (textured)
|
||||||
{
|
{
|
||||||
bindings.push_back(vk::DescriptorSetLayoutBinding(1, vk::DescriptorType::eCombinedImageSampler, 1, vk::ShaderStageFlagBits::eFragment));
|
bindings.push_back(vk::DescriptorSetLayoutBinding(1, vk::DescriptorType::eCombinedImageSampler, 1, vk::ShaderStageFlagBits::eFragment));
|
||||||
@ -392,10 +392,10 @@ namespace vk
|
|||||||
;
|
;
|
||||||
}
|
}
|
||||||
|
|
||||||
void updateDescriptorSets(vk::UniqueDevice &device, vk::UniqueDescriptorSet &descriptorSet, vk::DescriptorBufferInfo const* descriptorBufferInfo, vk::DescriptorImageInfo const* descriptorImageInfo)
|
void updateDescriptorSets(vk::UniqueDevice &device, vk::UniqueDescriptorSet &descriptorSet, vk::DescriptorType descriptorType, vk::DescriptorBufferInfo const* descriptorBufferInfo, vk::DescriptorImageInfo const* descriptorImageInfo)
|
||||||
{
|
{
|
||||||
std::vector<vk::WriteDescriptorSet> writeDescriptorSets;
|
std::vector<vk::WriteDescriptorSet> writeDescriptorSets;
|
||||||
writeDescriptorSets.push_back(vk::WriteDescriptorSet(descriptorSet.get(), 0, 0, 1, vk::DescriptorType::eUniformBuffer, nullptr, descriptorBufferInfo, nullptr));
|
writeDescriptorSets.push_back(vk::WriteDescriptorSet(descriptorSet.get(), 0, 0, 1, descriptorType, nullptr, descriptorBufferInfo, nullptr));
|
||||||
if (descriptorImageInfo)
|
if (descriptorImageInfo)
|
||||||
{
|
{
|
||||||
writeDescriptorSets.push_back(vk::WriteDescriptorSet(descriptorSet.get(), 1, 0, 1, vk::DescriptorType::eCombinedImageSampler, descriptorImageInfo, nullptr, nullptr));
|
writeDescriptorSets.push_back(vk::WriteDescriptorSet(descriptorSet.get(), 1, 0, 1, vk::DescriptorType::eCombinedImageSampler, descriptorImageInfo, nullptr, nullptr));
|
||||||
|
@ -91,10 +91,22 @@ namespace vk
|
|||||||
}
|
}
|
||||||
|
|
||||||
template <class T>
|
template <class T>
|
||||||
void copyToDevice(vk::UniqueDevice &device, vk::UniqueDeviceMemory &memory, T const* pData, size_t count)
|
void copyToDevice(vk::UniqueDevice &device, vk::UniqueDeviceMemory &memory, T const* pData, size_t count, size_t stride = sizeof(T))
|
||||||
|
{
|
||||||
|
assert(sizeof(T) <= stride);
|
||||||
|
uint8_t* deviceData = static_cast<uint8_t*>(device->mapMemory(memory.get(), 0, count * stride));
|
||||||
|
if (stride == sizeof(T))
|
||||||
{
|
{
|
||||||
uint8_t* deviceData = static_cast<uint8_t*>(device->mapMemory(memory.get(), 0, count * sizeof(T)));
|
|
||||||
memcpy(deviceData, pData, count * sizeof(T));
|
memcpy(deviceData, pData, count * sizeof(T));
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
for (size_t i = 0; i < count; i++)
|
||||||
|
{
|
||||||
|
memcpy(deviceData, &pData[i], sizeof(T));
|
||||||
|
deviceData += stride;
|
||||||
|
}
|
||||||
|
}
|
||||||
device->unmapMemory(memory.get());
|
device->unmapMemory(memory.get());
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -113,8 +125,8 @@ namespace vk
|
|||||||
vk::UniqueDeviceMemory allocateMemory(vk::UniqueDevice &device, vk::PhysicalDeviceMemoryProperties const& memoryProperties, vk::MemoryRequirements const& memoryRequirements, vk::MemoryPropertyFlags memoryPropertyFlags);
|
vk::UniqueDeviceMemory allocateMemory(vk::UniqueDevice &device, vk::PhysicalDeviceMemoryProperties const& memoryProperties, vk::MemoryRequirements const& memoryRequirements, vk::MemoryPropertyFlags memoryPropertyFlags);
|
||||||
vk::UniqueCommandPool createCommandPool(vk::UniqueDevice &device, uint32_t queueFamilyIndex);
|
vk::UniqueCommandPool createCommandPool(vk::UniqueDevice &device, uint32_t queueFamilyIndex);
|
||||||
vk::UniqueDebugReportCallbackEXT createDebugReportCallback(vk::UniqueInstance &instance);
|
vk::UniqueDebugReportCallbackEXT createDebugReportCallback(vk::UniqueInstance &instance);
|
||||||
vk::UniqueDescriptorPool createDescriptorPool(vk::UniqueDevice &device, bool textured = false);
|
vk::UniqueDescriptorPool createDescriptorPool(vk::UniqueDevice &device, vk::DescriptorType descriptorType = vk::DescriptorType::eUniformBuffer, bool textured = false);
|
||||||
vk::UniqueDescriptorSetLayout createDescriptorSetLayout(vk::UniqueDevice &device, bool textured = false);
|
vk::UniqueDescriptorSetLayout createDescriptorSetLayout(vk::UniqueDevice &device, vk::DescriptorType = vk::DescriptorType::eUniformBuffer, bool textured = false);
|
||||||
vk::UniqueDevice createDevice(vk::PhysicalDevice physicalDevice, uint32_t queueFamilyIndex, std::vector<std::string> const& extensions = {});
|
vk::UniqueDevice createDevice(vk::PhysicalDevice physicalDevice, uint32_t queueFamilyIndex, std::vector<std::string> const& extensions = {});
|
||||||
std::vector<vk::UniqueFramebuffer> createFramebuffers(vk::UniqueDevice &device, vk::UniqueRenderPass &renderPass, std::vector<vk::UniqueImageView> const& imageViews, vk::UniqueImageView &depthImageView, vk::Extent2D const& extent);
|
std::vector<vk::UniqueFramebuffer> createFramebuffers(vk::UniqueDevice &device, vk::UniqueRenderPass &renderPass, std::vector<vk::UniqueImageView> const& imageViews, vk::UniqueImageView &depthImageView, vk::Extent2D const& extent);
|
||||||
vk::UniquePipeline createGraphicsPipeline(vk::UniqueDevice &device, vk::UniquePipelineCache &pipelineCache, vk::UniqueShaderModule &vertexShaderModule, vk::UniqueShaderModule &fragmentShaderModule, uint32_t vertexStride, vk::UniquePipelineLayout &pipelineLayout, vk::UniqueRenderPass &renderPass);
|
vk::UniquePipeline createGraphicsPipeline(vk::UniqueDevice &device, vk::UniquePipelineCache &pipelineCache, vk::UniqueShaderModule &vertexShaderModule, vk::UniqueShaderModule &fragmentShaderModule, uint32_t vertexStride, vk::UniquePipelineLayout &pipelineLayout, vk::UniqueRenderPass &renderPass);
|
||||||
@ -129,7 +141,7 @@ namespace vk
|
|||||||
vk::Format pickColorFormat(std::vector<vk::SurfaceFormatKHR> const& formats);
|
vk::Format pickColorFormat(std::vector<vk::SurfaceFormatKHR> const& formats);
|
||||||
void setImageLayout(vk::UniqueCommandBuffer &commandBuffer, vk::Image image, vk::ImageAspectFlags aspectFlags, vk::ImageLayout oldImageLayout, vk::ImageLayout newImageLayout, vk::PipelineStageFlags sourceStageMask, vk::PipelineStageFlags destinationStageMask);
|
void setImageLayout(vk::UniqueCommandBuffer &commandBuffer, vk::Image image, vk::ImageAspectFlags aspectFlags, vk::ImageLayout oldImageLayout, vk::ImageLayout newImageLayout, vk::PipelineStageFlags sourceStageMask, vk::PipelineStageFlags destinationStageMask);
|
||||||
void submitAndWait(vk::UniqueDevice &device, vk::Queue queue, vk::UniqueCommandBuffer &commandBuffer);
|
void submitAndWait(vk::UniqueDevice &device, vk::Queue queue, vk::UniqueCommandBuffer &commandBuffer);
|
||||||
void updateDescriptorSets(vk::UniqueDevice &device, vk::UniqueDescriptorSet &descriptorSet, vk::DescriptorBufferInfo const* descriptorBufferInfo, vk::DescriptorImageInfo const* descriptorImageInfo = nullptr);
|
void updateDescriptorSets(vk::UniqueDevice &device, vk::UniqueDescriptorSet &descriptorSet, vk::DescriptorType descriptorType, vk::DescriptorBufferInfo const* descriptorBufferInfo, vk::DescriptorImageInfo const* descriptorImageInfo = nullptr);
|
||||||
|
|
||||||
#if defined(VK_USE_PLATFORM_WIN32_KHR)
|
#if defined(VK_USE_PLATFORM_WIN32_KHR)
|
||||||
HWND initializeWindow(std::string const& className, std::string const& windowName, LONG width, LONG height);
|
HWND initializeWindow(std::string const& className, std::string const& windowName, LONG width, LONG height);
|
||||||
|
Loading…
Reference in New Issue
Block a user