diff --git a/CMakeLists.txt b/CMakeLists.txt index da458ea..bcad1a4 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -41,11 +41,14 @@ DEPENDS ##----------------------------------------------------------------------------- list (APPEND sources vk.hpp + fwd.hpp object.cpp object.hpp + buffer.cpp buffer.hpp + callback.hpp command_buffer.cpp command_buffer.hpp command_pool.cpp diff --git a/callback.hpp b/callback.hpp new file mode 100644 index 0000000..4ac8244 --- /dev/null +++ b/callback.hpp @@ -0,0 +1,30 @@ +/* + * 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. + * + * Copyright: + * 2017, Danny Robson + */ + +#ifndef CRUFT_VK_CALLACK_HPP +#define CRUFT_VK_CALLACK_HPP + +#include "./object.hpp" +#include "./fwd.hpp" + +namespace cruft::vk { + struct debug_report : public owned { + using owned::owned; + }; +} + +#endif diff --git a/fwd.hpp b/fwd.hpp index 24ba2c2..2cb687c 100644 --- a/fwd.hpp +++ b/fwd.hpp @@ -39,6 +39,7 @@ namespace cruft::vk { struct command_pool; struct device; struct device_memory; + struct debug_report; struct event; struct fence; struct framebuffer; @@ -79,6 +80,7 @@ namespace cruft::vk { MAP0(FUNC, \ buffer, \ command_pool, \ + debug_report, \ device_memory, \ framebuffer, \ image_view, \ diff --git a/instance.hpp b/instance.hpp index e865d02..0e87336 100644 --- a/instance.hpp +++ b/instance.hpp @@ -46,15 +46,15 @@ namespace cruft::vk { util::view extensions); instance (const create_info_t &info); - template - T + template + FunctionT proc (const char *name) { auto ret = vkGetInstanceProcAddr (native (), name); if (!ret) throw vk::invalid_argument ("invalid procedure name"); - return reinterpret_cast (ret); + return reinterpret_cast (ret); } std::set extensions (void) const; diff --git a/tools/hello.cpp b/tools/hello.cpp index 7815678..622b822 100644 --- a/tools/hello.cpp +++ b/tools/hello.cpp @@ -14,6 +14,7 @@ #include #include #include +#include #include #include @@ -100,8 +101,9 @@ main (void) util::make_view (extensions.data (), extensions.data () + extensions.size ()) ); - { - VkDebugReportCallbackEXT callback; + load_traits (instance); + + auto callback = [&instance] () { VkDebugReportCallbackCreateInfoEXT debug_info {}; debug_info.sType = cruft::vk::structure_type_v; debug_info.flags = //VK_DEBUG_REPORT_INFORMATION_BIT_EXT | @@ -112,12 +114,8 @@ main (void) ; debug_info.pfnCallback = vk_debug_callback; - auto func = (decltype(&vkCreateDebugReportCallbackEXT))vkGetInstanceProcAddr (instance.native (),"vkCreateDebugReportCallbackEXT"); - - cruft::vk::error::try_func ( - *func, instance.native (), &debug_info, nullptr, &callback - ); - } + return cruft::vk::make_owned (instance, &debug_info, nullptr); + } (); auto pdevices = cruft::vk::physical_device::find (instance); auto &pdevice = pdevices[0]; diff --git a/traits.cpp b/traits.cpp index 4c1c4c4..5260dc0 100644 --- a/traits.cpp +++ b/traits.cpp @@ -17,5 +17,27 @@ #include "./traits.hpp" +#include "./instance.hpp" + /////////////////////////////////////////////////////////////////////////////// +#define INSTANTIATE(KLASS, NAME, FUNC) \ +decltype(FUNC)* cruft::vk::life_traits::NAME = nullptr + +INSTANTIATE(VkDebugReportCallbackEXT, create, vkCreateDebugReportCallbackEXT); +INSTANTIATE(VkDebugReportCallbackEXT, destroy, vkDestroyDebugReportCallbackEXT); + + +/////////////////////////////////////////////////////////////////////////////// +void +cruft::vk::load_traits (instance &i) +{ + #define LOAD(KLASS,NAME,FUNC) \ + try { \ + cruft::vk::life_traits::NAME = i.proc (#FUNC); \ + } catch (const vk::invalid_argument&) \ + { ; } + + LOAD(VkDebugReportCallbackEXT, create, vkCreateDebugReportCallbackEXT); + LOAD(VkDebugReportCallbackEXT, destroy, vkDestroyDebugReportCallbackEXT); +} diff --git a/traits.hpp b/traits.hpp index 08f70c5..8bbd7b5 100644 --- a/traits.hpp +++ b/traits.hpp @@ -54,6 +54,7 @@ namespace cruft::vk { template <> struct native_traits { using type = VkShaderModule; }; template <> struct native_traits { using type = VkSurfaceKHR; }; template <> struct native_traits { using type = VkSwapchainKHR; }; + template <> struct native_traits { using type = VkDebugReportCallbackEXT; }; //------------------------------------------------------------------------- template <> @@ -172,6 +173,7 @@ namespace cruft::vk { template <> struct owner_traits { using type = device; }; template <> struct owner_traits> { using type = device; }; template <> struct owner_traits> { using type = device; }; + template <> struct owner_traits { using type = instance; }; template using owner_t = typename owner_traits::type; @@ -316,6 +318,22 @@ namespace cruft::vk { }; + template <> struct life_traits { + static decltype(vkCreateDebugReportCallbackEXT) *create; + static decltype(vkDestroyDebugReportCallbackEXT) *destroy; + }; + + + // loads all extension function pointers from an instance into the + // appropriate life_traits pointers where available. + // + // this is unambigiously the wrong way of doing things: each instance may + // have their own function pointers to each of the extension methods. + // + // but... we only support one instance for the time being, and this easier. + void load_traits (instance&); + + /////////////////////////////////////////////////////////////////////////// template struct wrapper_traits : public life_traits> { }; @@ -341,6 +359,7 @@ namespace cruft::vk { /// describes the functions required to enumerate native types template struct enum_traits { }; + template <> struct enum_traits { static constexpr auto &enumerate = vkEnumeratePhysicalDevices; };