diff --git a/CMakeLists.txt b/CMakeLists.txt index e0d59ed..6305291 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -88,7 +88,6 @@ fennec_add_sources( include/fennec/core/logger.h source/core/logger.cpp include/fennec/core/version.h - include/fennec/core/system.h @@ -150,12 +149,14 @@ fennec_add_sources( include/fennec/lang/declval.h include/fennec/lang/function.h include/fennec/lang/hashing.h + include/fennec/lang/integer.h include/fennec/lang/intrinsics.h include/fennec/lang/limits.h include/fennec/lang/numeric_transforms.h include/fennec/lang/metasequences.h include/fennec/lang/ranges.h include/fennec/lang/static_constructor.h + include/fennec/lang/system.h include/fennec/lang/type_identity.h include/fennec/lang/type_operators.h include/fennec/lang/type_sequences.h @@ -163,7 +164,6 @@ fennec_add_sources( include/fennec/lang/type_transforms.h include/fennec/lang/types.h include/fennec/lang/utility.h - include/fennec/lang/integer.h include/fennec/lang/assert.h source/lang/assert.cpp @@ -179,14 +179,15 @@ fennec_add_sources( # RTTI ================================================================================================================= - include/fennec/rtti/typeid.h - include/fennec/rtti/type_data.h - include/fennec/rtti/type.h - include/fennec/rtti/enable.h include/fennec/rtti/forward.h - include/fennec/rtti/typelist.h - include/fennec/rtti/type_registry.h + include/fennec/rtti/enable.h include/fennec/rtti/singleton.h + include/fennec/rtti/this_t.h + include/fennec/rtti/type.h + include/fennec/rtti/type_data.h + include/fennec/rtti/type_registry.h + include/fennec/rtti/typeid.h + include/fennec/rtti/typelist.h include/fennec/rtti/detail/_constants.h @@ -268,6 +269,7 @@ fennec_add_sources( include/fennec/string/locale.h include/fennec/string/cstring.h include/fennec/string/string.h + include/fennec/string/string_view.h include/fennec/string/detail/_ctype.h @@ -314,7 +316,9 @@ add_subdirectory(test) add_library(fennec STATIC ${FENNEC_SOURCES} - include/fennec/rtti/this_t.h + include/fennec/renderers/vulkan/lib/logical_device.h + include/fennec/renderers/vulkan/lib/physical_device_properties.h + include/fennec/renderers/vulkan/lib/physical_device_features.h ) add_dependencies(fennec metaprogramming fennec-dependencies) diff --git a/README.md b/README.md index 1dc0205..73cfb5f 100644 --- a/README.md +++ b/README.md @@ -155,7 +155,6 @@ is also a viable IDE but involves some extra setup. |------------------------------|----------------------------------------------------------------------------------------------------------| | C/C++ Compiler | GCC/G++ is the compiler that fennec is designed around, however, Clang, MSVC, and MinGW may also be used | | CMake | The build manager used by the engine | -| Volk[*](#opt) | The Vulkan loader Volk, includes necessary headers for Vulkan. | | A build system | Any build system will work, however, `build.sh` uses Ninja by default. | | A memory debugger | Any memory debugger will work, however, `test.sh` uses Valgrind by default. | | Doxygen[*](#opt) | Doxygen is required for building the documentation for fennec. | diff --git a/cmake/build.cmake b/cmake/build.cmake index fcfbb6c..3bd599a 100644 --- a/cmake/build.cmake +++ b/cmake/build.cmake @@ -18,11 +18,22 @@ # this script handles functionality related to the build process and its info +# Acquire the build name string(TOLOWER ${CMAKE_BUILD_TYPE} FENNEC_BUILD_NAME) message(STATUS "Build: ${FENNEC_BUILD_NAME}") +# Add build name to the compile definitions +fennec_add_definitions(FENNEC_BUILD_NAME="${FENNEC_BUILD_NAME}") + +# Check if building for debug if(${FENNEC_BUILD_NAME} MATCHES "debug") - list(APPEND FENNEC_COMPILE_DEFINITIONS FENNEC_RELEASE=false) + fennec_add_definitions(FENNEC_RELEASE=false FENNEC_DEBUG=true) + +# Release with debug info +elseif(${FENNEC_BUILD_NAME} MATCHES "relwithdebinfo") + fennec_add_definitions(FENNEC_RELEASE=true FENNEC_DEBUG=true) + +# Any others are considered release without debugging else() - list(APPEND FENNEC_COMPILE_DEFINITIONS FENNEC_RELEASE=true) -endif() \ No newline at end of file + fennec_add_definitions(FENNEC_RELEASE=true FENNEC_DEBUG=false) +endif() diff --git a/cmake/clang.cmake b/cmake/clang.cmake new file mode 100644 index 0000000..b85ffa3 --- /dev/null +++ b/cmake/clang.cmake @@ -0,0 +1,38 @@ +# ====================================================================================================================== +# fennec, a free and open source game engine +# Copyright © 2025 - 2026 Medusa Slockbower +# +# This program is free software: you can redistribute it and/or modify +# it under the terms of the GNU General Public License as published by +# the Free Software Foundation, either version 3 of the License, or +# (at your option) any later version. +# +# This program is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with this program. If not, see . +# ====================================================================================================================== + +# this script sets flags and variables for llvm compilers + +# Receive all warnings and treat as errors +add_compile_options("-Wall" "-Wextra" "-pedantic" "-Werror" "-fms-extensions") + +# Use relative directories to hide the user's directory +fennec_add_compile_options("-ffile-prefix-map=${FENNEC_SOURCE_DIR}=.") + +# Disable STDLIB, Exceptions, and RTTI, we implement our own. Also include diagnostics and pthread. +fennec_add_link_options("-nostdlib" "-fno-exceptions" "-fno-rtti" "-fdiagnostics-all-candidates" "-pthread") + +# Base definitions for Clang +fennec_add_definitions( + _GLIBCXX_INCLUDE_NEXT_C_HEADERS=1 + FENNEC_COMPILER_CLANG=1 + FENNEC_GLIBC=1 + FENNEC_NO_INLINE=[[clang::noinline]] + FENNEC_FUNCTION_NAME=__PRETTY_FUNCTION__ +) + diff --git a/cmake/compiler.cmake b/cmake/compiler.cmake index 72c9496..a0026d8 100644 --- a/cmake/compiler.cmake +++ b/cmake/compiler.cmake @@ -18,13 +18,27 @@ # this script finds the compiler being used +# Send a message letting us know the compiler and its version message(STATUS "Compiler: ${CMAKE_CXX_COMPILER_ID} ${CMAKE_CXX_COMPILER_VERSION}") +# Add definitions for the compiler fennec_add_definitions( FENNEC_LONG_COMPILER_NAME="${CMAKE_CXX_COMPILER_ID} ${CMAKE_SYSTEM_NAME} ${CMAKE_SYSTEM_PROCESSOR}" ) +# GCC if(${CMAKE_CXX_COMPILER_ID} MATCHES "GNU") -set(FENNEC_COMPILER "GCC") -include("${FENNEC_SOURCE_DIR}/cmake/gcc.cmake") + set(FENNEC_COMPILER "GCC") + include("${FENNEC_SOURCE_DIR}/cmake/gcc.cmake") endif() + +# Clang +if(${CMAKE_CXX_COMPILER_ID} MATCHES "Clang") + set(FENNEC_COMPILER "Clang") + include("${FENNEC_SOURCE_DIR}/cmake/clang.cmake") +endif() + + + +# TODO: MSVC & MinGW + diff --git a/cmake/gcc.cmake b/cmake/gcc.cmake index 405f674..226efe4 100644 --- a/cmake/gcc.cmake +++ b/cmake/gcc.cmake @@ -18,15 +18,20 @@ # this script sets flags and variables for gnu and gnu-like compilers +# Receive all warnings and treat as errors add_compile_options("-Wall" "-Wextra" "-pedantic" "-Werror" "-fms-extensions") +# Use relative directories to hide the user's directory fennec_add_compile_options("-ffile-prefix-map=${FENNEC_SOURCE_DIR}=.") +# Disable STDLIB, Exceptions, and RTTI, we implement our own. Also include diagnostics and pthread. fennec_add_link_options("-nostdlib" "-fno-exceptions" "-fno-rtti" "-fdiagnostics-all-candidates" "-pthread") +# Base definitions for GCC fennec_add_definitions( _GLIBCXX_INCLUDE_NEXT_C_HEADERS=1 FENNEC_COMPILER_GCC=1 + FENNEC_GLIBC=1 FENNEC_NO_INLINE=[[gnu::noinline]] FENNEC_FUNCTION_NAME=__PRETTY_FUNCTION__ ) diff --git a/cmake/linux.cmake b/cmake/linux.cmake index c1d023c..83afe35 100644 --- a/cmake/linux.cmake +++ b/cmake/linux.cmake @@ -33,9 +33,11 @@ macro(fennec_check_platform) include/fennec/platform/linux/platform.h source/platform/linux/platform.cpp ) + # Add display and graphics for client builds. if(FENNEC_USER_CLIENT) include("${FENNEC_SOURCE_DIR}/cmake/wayland.cmake") + fennec_init_graphics() fennec_check_wayland() fennec_init_graphics() endif() diff --git a/cmake/opengl.cmake b/cmake/opengl.cmake index e20eae6..f73562e 100644 --- a/cmake/opengl.cmake +++ b/cmake/opengl.cmake @@ -18,9 +18,10 @@ find_package(OpenGL) +# Check if EGL is desired if(FENNEC_GRAPHICS_WANT_EGL) fennec_add_sources( - include/fennec/platform/opengl/egl/fwd.h + include/fennec/platform/opengl/egl/forward.h include/fennec/platform/opengl/egl/error.h include/fennec/platform/opengl/egl/context.h source/platform/opengl/egl/context.cpp include/fennec/platform/opengl/egl/surface.h source/platform/opengl/egl/surface.cpp @@ -29,15 +30,24 @@ if(FENNEC_GRAPHICS_WANT_EGL) ) endif() +# Check that we found OpenGL if(TARGET OpenGL::GL) + + # Link & add definitions for OpenGL fennec_add_link_libraries(OpenGL::GL) fennec_add_definitions(FENNEC_GRAPHICS_OPENGL=1) + # Cmake Definition for OpenGL detection + set(FENNEC_FOUND_OPENGL TRUE) + + # Add OpenGL sources fennec_add_sources( include/fennec/platform/opengl/glad/gl.h source/platform/opengl/glad/gl.c include/fennec/renderers/opengl/glcontext.h source/renderers/opengl/glcontext.cpp ) else() + + # OpenGL is required if included. message(FATAL_ERROR "No Suitable OpenGL implementation found.") endif() \ No newline at end of file diff --git a/cmake/platform.cmake b/cmake/platform.cmake index 2c70846..03a1cdb 100644 --- a/cmake/platform.cmake +++ b/cmake/platform.cmake @@ -28,7 +28,7 @@ if(${CMAKE_SYSTEM_NAME} MATCHES "Linux") include("${FENNEC_SOURCE_DIR}/cmake/linux.cmake") endif () -# Graphics APIs +# Include graphics APIs Second time for any platform specific requirements macro(fennec_init_graphics) include("${FENNEC_SOURCE_DIR}/cmake/opengl.cmake") include("${FENNEC_SOURCE_DIR}/cmake/vulkan.cmake") diff --git a/cmake/version.cmake b/cmake/version.cmake index b48d231..9c7c280 100644 --- a/cmake/version.cmake +++ b/cmake/version.cmake @@ -18,12 +18,15 @@ # this script contains the main version +# Fennec Version Definition +# These should only get updated whenever a new release occurs set(FENNEC_VERSION_MAJOR 0) set(FENNEC_VERSION_MINOR 1) set(FENNEC_VERSION_PATCH 0) set(FENNEC_VERSION_STRING "${FENNEC_VERSION_MAJOR}.${FENNEC_VERSION_MINOR}.${FENNEC_VERSION_PATCH}") math(EXPR FENNEC_VERSION_NUM "(${FENNEC_VERSION_MAJOR} << 16) | (${FENNEC_VERSION_MINOR} << 8) | ${FENNEC_VERSION_PATCH}") +# Define the versions for compilation list(APPEND FENNEC_COMPILE_DEFINITIONS FENNEC_VERSION_MAJOR=${FENNEC_VERSION_MAJOR} FENNEC_VERSION_MINOR=${FENNEC_VERSION_MINOR} diff --git a/cmake/vulkan.cmake b/cmake/vulkan.cmake index 39f49a9..035a785 100644 --- a/cmake/vulkan.cmake +++ b/cmake/vulkan.cmake @@ -16,24 +16,41 @@ # along with this program. If not, see . # ====================================================================================================================== -find_package(Vulkan COMPONENTS glslang volk) +find_package(Vulkan COMPONENTS glslang) +# MoltenVK for Apple Products if(FENNEC_GRAPHICS_WANT_MOLTENVK) find_package(Vulkan COMPONENTS MoltenVK) endif() -if( TARGET Vulkan::Headers AND TARGET Vulkan::volk # Base Headers and Meta-Loader + +# Headers and Loaders +if( TARGET Vulkan::Headers # Base Headers and Meta-Loader AND TARGET Vulkan::glslang # GLSL Compilation AND (NOT FENNEC_GRAPHICS_WANT_MOLTENVK OR TARGET Vulkan::MoltenVK) ) - fennec_add_link_libraries(Vulkan::volk Vulkan::glslang) + # Link & Define Vulkan Libraries + fennec_add_link_libraries(Vulkan::glslang) fennec_add_definitions(FENNEC_GRAPHICS_VULKAN=1) - fennec_add_sources( - include/fennec/renderers/vulkan/lib/app_info.h - include/fennec/renderers/vulkan/lib/instance.h + # Cmake Definition for Vulkan detection + set(FENNEC_FOUND_VULKAN TRUE) - include/fennec/renderers/vulkan/vkcontext.h include/fennec/renderers/vulkan/vkcontext.cpp + # Add Vulkan Sources + fennec_add_sources( + include/fennec/renderers/vulkan/lib/forward.h + + include/fennec/renderers/vulkan/lib/app_info.h + include/fennec/renderers/vulkan/lib/debug.h + include/fennec/renderers/vulkan/lib/enum.h + include/fennec/renderers/vulkan/lib/instance.h + include/fennec/renderers/vulkan/lib/physical_device.h + include/fennec/renderers/vulkan/lib/surface.h + + include/fennec/platform/vulkan/volk/volk.h source/platform/vulkan/volk/volk.c + + include/fennec/renderers/vulkan/vkcontext.h source/renderers/vulkan/vkcontext.cpp + include/fennec/renderers/vulkan/vksurface.h source/renderers/vulkan/vksurface.cpp ) else() message(WARNING "No Suitable Vulkan implementation found.") diff --git a/cmake/wayland.cmake b/cmake/wayland.cmake index 5bedb6a..444ea7a 100644 --- a/cmake/wayland.cmake +++ b/cmake/wayland.cmake @@ -70,11 +70,12 @@ macro(fennec_check_wayland) NAMES wayland-egl libwayland-egl ) - + # Check that we have found everything needed for Wayland if( (WAYLAND_CLIENT_INCLUDE_DIR AND WAYLAND_CLIENT_LIBRARY AND WAYLAND_SCANNER) AND (WAYLAND_EGL_INCLUDE_DIR AND WAYLAND_EGL_LIBRARY)) message(STATUS "Found Wayland: ${WAYLAND_CLIENT_LIBRARY}") + # Wayland Directories set(WAYLAND_PROTOCOLS_DIR ${FENNEC_SOURCE_DIR}/include/fennec/platform/linux/wayland/lib/protocols) set(WAYLAND_HEADERS_DIR ${FENNEC_SOURCE_DIR}/include/fennec/platform/linux/wayland/lib/headers) set(WAYLAND_SOURCES_DIR ${FENNEC_SOURCE_DIR}/source/platform/linux/wayland/lib/sources) @@ -117,7 +118,7 @@ macro(fennec_check_wayland) include/fennec/platform/linux/wayland/lib/loader.h source/platform/linux/wayland/lib/loader.cpp # Fennec Files - include/fennec/platform/linux/wayland/fwd.h + include/fennec/platform/linux/wayland/forward.h include/fennec/platform/linux/wayland/server.h source/platform/linux/wayland/server.cpp include/fennec/platform/linux/wayland/window.h source/platform/linux/wayland/window.cpp @@ -126,6 +127,12 @@ macro(fennec_check_wayland) include/fennec/platform/linux/wayland/egl/surface.h source/platform/linux/wayland/egl/surface.cpp ) + if(FENNEC_FOUND_VULKAN) + fennec_add_sources( + include/fennec/platform/linux/wayland/vulkan/context.h source/platform/linux/wayland/vulkan/context.cpp + ) + endif () + fennec_add_definitions( FENNEC_HAS_WAYLAND=1 FENNEC_LIB_WAYLAND="${WAYLAND_CLIENT_LIBRARY}" diff --git a/doxy/Doxyfile.in b/doxy/Doxyfile.in index fc266aa..5168a3b 100644 --- a/doxy/Doxyfile.in +++ b/doxy/Doxyfile.in @@ -283,7 +283,8 @@ TAB_SIZE = 4 # with the commands \{ and \} for these it is advised to use the version @{ and # @} or use a double escape (\\{ and \\}) -ALIASES = +ALIASES = emph{1}="\f$\textbf{\1}\f$" \ + math{1}="\f$\1\f$" # Set the OPTIMIZE_OUTPUT_FOR_C tag to YES if your project consists of C sources # only. Doxygen will then generate output that is more tailored for C. For diff --git a/include/fennec/containers/array.h b/include/fennec/containers/array.h index d15b20b..4f27970 100644 --- a/include/fennec/containers/array.h +++ b/include/fennec/containers/array.h @@ -44,20 +44,19 @@ namespace fennec /// \brief Data Structure that defines a compile-time allocated array /// /// \details -/// | Property | Value | -/// |:-----------:|:----------:| -/// | stable | ✅ | -/// | dynamic | ⛔ | -/// | homogeneous | ✅ | -/// | distinct | ⛔ | -/// | ordered | ⛔ | -/// | space | \f$O(N)\f$ | -/// | linear | ✅ | -/// | access | \f$O(1)\f$ | -/// | find | \f$O(N)\f$ | -/// | insertion | ⛔ | -/// | deletion | ⛔ | -/// | space | \f$O(N)\f$ | +/// | Property | Value | +/// |:-----------:|:-----------:| +/// | stable | ✅ | +/// | dynamic | ⛔ | +/// | homogeneous | ✅ | +/// | distinct | ⛔ | +/// | ordered | ⛔ | +/// | linear | ✅ | +/// | space | \emph{O(N)} | +/// | access | \emph{O(1)} | +/// | find | \emph{O(N)} | +/// | insertion | ⛔ | +/// | deletion | ⛔ | /// /// \tparam ValueT value type /// \tparam N number of elements @@ -70,7 +69,7 @@ public: /// \name Definitions /// @{ - using value_t = ValueT; //!< Alias for \f$ValueT\f$ + using value_t = ValueT; //!< Alias for \emph{ValueT} /// @} @@ -96,21 +95,21 @@ public: /// /// \brief Returns the number of elements in the array. - /// \returns \f$N\f$ + /// \returns \emph{N} /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// - [[nodiscard]] constexpr size_t size() const { return N; } + constexpr size_t size() const { return N; } /// - /// \brief Returns \f$true\f$ when the array is empty - /// \returns \f$ElemV == 0\f$ + /// \brief Returns \emph{true} when the array is empty + /// \returns \math{\textbf{ElemV} == 0} /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// - [[nodiscard]] constexpr bool_t is_empty() const { return N == 0; } + constexpr bool_t is_empty() const { return N == 0; } /// @} @@ -128,7 +127,7 @@ public: /// \return reference to the requested element /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr value_t& operator[](size_t i) { assertd(i < N, "Array Out of Bounds"); @@ -142,7 +141,7 @@ public: /// \return reference to the requested element /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr const value_t& operator[](size_t i) const { assertd(i < N, "Array Out of Bounds"); @@ -150,10 +149,10 @@ public: } /// - /// \returns A reference to \f$data[0]\f$ + /// \returns A reference to \math{\textbf{data}[0]} /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr value_t& front() { return data[0]; @@ -161,20 +160,20 @@ public: /// /// \brief Access the first element - /// \returns A const-qualified reference to \f$data[0]\f$ + /// \returns A const-qualified reference to \math{\textbf{data}[0]} /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr const value_t& front() const { return data[0]; } /// - /// \returns A reference to \f$data[N - 1]\f$ + /// \returns A reference to \math{\textbf{data}[\textbf{N} - 1]} /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr value_t& back() { return data[N - 1]; @@ -182,10 +181,10 @@ public: /// /// \brief Access the last element - /// \returns A const-qualified reference to \f$data[N - 1]\f$ + /// \returns A const-qualified reference to \math{\textbf{data}[\textbf{N} - 1]} /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr const value_t& back() const { return data[N - 1]; @@ -205,7 +204,7 @@ public: /// \brief Checks if all elements in the arrays are equal /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// friend constexpr bool_t operator==(const array& lhs, const array& rhs) { return array::_compare(lhs, rhs, make_index_metasequence{}); @@ -215,7 +214,7 @@ public: /// \brief Checks if any element in the arrays is not equal /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// friend constexpr bool_t operator!=(const array& lhs, const array& rhs) { return not array::_compare(lhs, rhs, make_index_metasequence{}); @@ -234,18 +233,18 @@ public: /// \returns A pointer to the first element of the array /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr value_t* begin() { return data; } /// - /// \brief C++ Iterator Specification \f$begin()\f$ + /// \brief C++ Iterator Specification \emph{begin()} /// \returns A const-qualified pointer to the first element of the array /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr const value_t* begin() const { return data; @@ -255,18 +254,18 @@ public: /// \returns A pointer to one after the end of the array /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr value_t* end() { return data + N; } /// - /// \brief C++ Iterator Specification \f$end()\f$ + /// \brief C++ Iterator Specification \emph{end()} /// \returns A const-qualified pointer to one after the end of the array /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr const value_t* end() const { return data + N; diff --git a/include/fennec/containers/bintree.h b/include/fennec/containers/bintree.h index 8e92753..ae861b5 100644 --- a/include/fennec/containers/bintree.h +++ b/include/fennec/containers/bintree.h @@ -31,34 +31,34 @@ #ifndef FENNEC_CONTAINERS_BINTREE_H #define FENNEC_CONTAINERS_BINTREE_H +#include + #include #include #include #include #include -#include namespace fennec { /// -/// \brief Structure defining a binary tree +/// \brief Structure defining an in-array binary tree /// /// \details -/// | Property | Value | -/// |:-----------:|:----------:| -/// | stable | ⛔ | -/// | dynamic | ✅ | -/// | homogeneous | ✅ | -/// | distinct | ⛔ | -/// | ordered | ⛔ | -/// | space | \f$O(N)\f$ | -/// | linear | ⛔ | -/// | access | \f$O(1)\f$ | -/// | find | \f$O(N)\f$ | -/// | insertion | \f$O(1)\f$ | -/// | deletion | \f$O(1)\f$ | -/// | space | \f$O(N)\f$ | +/// | Property | Value | +/// |:-----------:|:-----------:| +/// | stable | ⛔ | +/// | dynamic | ✅ | +/// | homogeneous | ✅ | +/// | distinct | ⛔ | +/// | ordered | ⛔ | +/// | linear | ⛔ | +/// | space | \emph{O(N)} | +/// | access | \emph{O(1)} | +/// | find | \emph{O(N)} | +/// | insertion | \emph{O(1)} | +/// | deletion | \emph{O(1)} | /// /// \tparam TypeT The data type /// \tparam AllocT An allocator class @@ -107,7 +107,7 @@ public: /// \details The underlying allocation is not initialized. /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr bintree() : _table() @@ -120,10 +120,10 @@ public: /// \brief Move Constructor, takes ownership of a tree /// \param tree The tree to take ownership of /// - /// \details Takes ownership of the underlying allocation of \f$tree\f$ + /// \details Takes ownership of the underlying allocation of \emph{tree} /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr bintree(bintree&& tree) noexcept : _table(fennec::move(tree._table)) @@ -136,10 +136,10 @@ public: /// \brief Copy Constructor, copies a tree /// \param tree The tree to copy /// - /// \details Copies the contents of \f$tree\f$ into a new tree. Invokes copy constructor. + /// \details Copies the contents of \emph{tree} into a new tree. Invokes copy constructor. /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// constexpr bintree(const bintree& tree) : _table(tree._table.capacity()) @@ -173,10 +173,10 @@ public: /// /// \brief Destructor, clears the tree /// - /// \details Clears the contents of \f$tree\f$. Invokes destructor. + /// \details Clears the contents of \emph{tree}. Invokes destructor. /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// constexpr ~bintree() { clear(); @@ -195,17 +195,17 @@ public: /// \returns The number of elements in the tree /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr size_t size() const { return _size; } /// - /// \returns \f$true\f$ when there are no elements in the tree, \f$false\f$ otherwise. + /// \returns \emph{true} when there are no elements in the tree, \emph{false} otherwise. /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr bool is_empty() const { return _size == 0; @@ -215,17 +215,17 @@ public: /// \returns The capacity of the underlying allocation /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr size_t capacity() const { return _table.capacity(); } /// - /// \returns The next id to be returned by \f$insert\f$ or \f$emplace\f$. + /// \returns The next id to be returned by `bintree::insert` or `bintree::emplace`. /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr size_t next_id() const { size_t i = _size; @@ -236,10 +236,10 @@ public: } /// - /// \returns The next id to be returned by \f$insert\f$ or \f$emplace\f$. + /// \returns The next id to be returned by `bintree::insert` or `bintree::emplace`. /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr size_t root() const { return _root; @@ -257,10 +257,10 @@ public: /// /// \param i The node id - /// \returns The parent of node \f$i\f$ + /// \returns The parent of node \emph{i} /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr size_t parent(size_t i) const { return i == npos ? npos : _table[i].parent; @@ -268,10 +268,10 @@ public: /// /// \param i The node id - /// \returns The grandparent of node \f$i\f$ + /// \returns The grandparent of node \emph{i} /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr size_t grandparent(size_t i) const { return parent(parent(i)); @@ -279,10 +279,10 @@ public: /// /// \param i The node id - /// \returns The left child of node \f$i\f$ + /// \returns The left child of node \emph{i} /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr size_t left(size_t i) const { return i == npos ? npos : _table[i].child[false]; @@ -290,10 +290,10 @@ public: /// /// \param i The node id - /// \returns The right child of node \f$i\f$ + /// \returns The right child of node \emph{i} /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr size_t right(size_t i) const { return i == npos ? npos : _table[i].child[true]; @@ -301,11 +301,11 @@ public: /// /// \param i The node id - /// \param dir The direction to go \f$true\f$ for right, \f$false\f$ for left - /// \returns The child in the direction specified by \f$dir\f$ + /// \param dir The direction to go \emph{true} for right, \emph{false} for left + /// \returns The child in the direction specified by \emph{dir} /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr size_t child(size_t i, bool dir) const { return i == npos ? npos : _table[i].child[dir]; @@ -313,10 +313,10 @@ public: /// /// \param i The node id - /// \returns \f$true\f$ if \f$i\f$ is the right node of \f$parent(i)\f$, \f$false\f$ otherwise + /// \returns \emph{true} if \emph{i} is the right node of \emph{parent(i)}, \emph{false} otherwise /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr bool side(size_t i) const { return i == npos ? false : i == right(_parent(i)); @@ -324,10 +324,10 @@ public: /// /// \param i The id of the node - /// \returns The id of the sibling of \f$i\f$ + /// \returns The id of the sibling of \emph{i} /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr size_t sibling(size_t i) const { if (i == npos) { @@ -337,16 +337,16 @@ public: return npos; } size_t p = _parent(i); - bool d = i == _right(p); + const bool d = i == _right(p); return _child(p, !d); } /// /// \param i The node id - /// \returns The depth of node \f$i\f$ + /// \returns The depth of node \emph{i} /// /// \par Complexity - /// \f$O(\log n)\f$ + /// \emph{O(\log n)} /// constexpr size_t depth(size_t i) const { size_t d = 0; @@ -359,10 +359,10 @@ public: /// /// \param i The node id - /// \returns The id of the left-most node of \f$i\f$ + /// \returns The id of the left-most node of \emph{i} /// /// \par Complexity - /// \f$O(\log n)\f$ + /// \emph{O(\log n)} /// constexpr size_t left_most(size_t i) const { if (i >= _table.size()) { @@ -376,10 +376,10 @@ public: /// /// \param i The node id - /// \returns The id of the right-most node of \f$i\f$ + /// \returns The id of the right-most node of \emph{i} /// /// \par Complexity - /// \f$O(\log n)\f$ + /// \emph{O(\log n)} /// constexpr size_t right_most(size_t i) const { if (i >= _table.size()) { @@ -402,10 +402,10 @@ public: /// /// \param i The node id - /// \returns a reference to the value of node \f$i\f$ + /// \returns a reference to the value of node \emph{i} /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr value_t& operator[](size_t i) { assertd(i < _table.size(), "Index out of bounds."); @@ -415,10 +415,10 @@ public: /// /// \details Node access /// \param i The node id - /// \returns a reference to the value of node \f$i\f$ + /// \returns a reference to the value of node \emph{i} /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr const value_t& operator[](size_t i) const { assertd(i < _table.size(), "Index out of bounds."); @@ -435,40 +435,40 @@ public: /// @{ /// - /// \details If the left node of \f$p\f$ already exists, the move assignment operator is used instead + /// \details If the left node of \emph{p} already exists, the move assignment operator is used instead /// \param p The parent node /// \param val The object to move into the new node /// \returns The id of the new node /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr size_t insert_left(size_t p, value_t&& val) { return this->_insert_left(p, fennec::forward(val)); } /// - /// \details If the left node of \f$p\f$ already exists, the copy assignment operator is used instead + /// \details If the left node of \emph{p} already exists, the copy assignment operator is used instead /// \param p The parent node /// \param val The object to copy to the new node /// \returns The id of the new node /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr size_t insert_left(size_t p, const value_t& val) { return this->_insert_left(p, val); } /// - /// \brief Left Insertion, constructs a new node as the left child of \f$p\f$ - /// \details If the left node of \f$p\f$ already exists, the move assignment operator is used instead + /// \brief Left Insertion, constructs a new node as the left child of \emph{p} + /// \details If the left node of \emph{p} already exists, the move assignment operator is used instead /// \param p The parent node /// \param args The arguments to construct the new node with /// \returns The id of the new node /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// template constexpr size_t emplace_left(size_t p, ArgsT&&...args) { @@ -476,40 +476,40 @@ public: } /// - /// \details If the right node of \f$p\f$ already exists, the move assignment operator is used instead + /// \details If the right node of \emph{p} already exists, the move assignment operator is used instead /// \param p The parent node /// \param val The object to move into the new node /// \returns The id of the new node /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr size_t insert_right(size_t p, value_t&& val) { return this->_insert_right(p, fennec::forward(val)); } /// - /// \details If the right node of \f$p\f$ already exists, the copy assignment operator is used instead + /// \details If the right node of \emph{p} already exists, the copy assignment operator is used instead /// \param p The parent node /// \param val The object to copy to the new node /// \returns The id of the new node /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr size_t insert_right(size_t p, const value_t& val) { return this->_insert_right(p, val); } /// - /// \brief Right Insertion, constructs a new node as the right child of \f$p\f$ - /// \details If the right node of \f$p\f$ already exists, the move assignment operator is used instead + /// \brief Right Insertion, constructs a new node as the right child of \emph{p} + /// \details If the right node of \emph{p} already exists, the move assignment operator is used instead /// \param p The parent node /// \param args The arguments to construct the new node with /// \returns The id of the new node /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// template constexpr size_t emplace_right(size_t p, ArgsT&&...args) { @@ -519,21 +519,21 @@ public: /// - /// \brief Perform a Tree Rotation at \f$i\f$ in the specified direction + /// \brief Perform a Tree Rotation at \emph{i} in the specified direction /// \param sub The root node for the rotation - /// \param dir The direction to rotate, \f$true\f$ for right, \f$false\f$ for left + /// \param dir The direction to rotate, \emph{true} for right, \emph{false} for left /// \returns the new root node /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr size_t rotate(size_t sub, bool dir) { if (sub == npos) { return npos; } - size_t sub_parent = _parent(sub); - size_t new_root = _child(sub, not dir); - size_t new_child = _child(new_root, dir); + const size_t sub_parent = _parent(sub); + const size_t new_root = _child(sub, not dir); + const size_t new_child = _child(new_root, dir); _child(sub, not dir) = new_child; if (new_child != npos) { @@ -552,43 +552,43 @@ public: } /// - /// \details If the child of \f$p\f$ already exists, the move assignment operator is used instead + /// \details If the child of \emph{p} already exists, the move assignment operator is used instead /// \param parent The parent node /// \param side The side to insert on /// \param val The object to move into the new node /// \returns The id of the new node /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr size_t insert(size_t parent, bool side, value_t&& val) { return this->_insert(parent, side, fennec::forward(val)); } /// - /// \details If the child of \f$p\f$ already exists, the copy assignment operator is used instead + /// \details If the child of \emph{p} already exists, the copy assignment operator is used instead /// \param parent The parent node /// \param side The side to insert on /// \param val The object to copy to the new node /// \returns The id of the new node /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr size_t insert(size_t parent, bool side, const value_t& val) { return this->_insert(parent, side, val); } /// - /// \brief Insertion, constructs a new node as the child of \f$p\f$ - /// \details If the child of \f$p\f$ already exists, the move assignment operator is used instead + /// \brief Insertion, constructs a new node as the child of \emph{p} + /// \details If the child of \emph{p} already exists, the move assignment operator is used instead /// \param parent The parent node /// \param side The side to insert on /// \param args The arguments to construct the new node with /// \returns The id of the new node /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// template constexpr size_t emplace(size_t parent, bool side, ArgsT&&...args) { @@ -599,7 +599,7 @@ public: /// \brief Clears the tree, destroying all elements /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// constexpr void clear() { list queue; @@ -636,16 +636,16 @@ public: /// /// \details - /// The visitor should accept a reference to a value of type \f$TypeT\f$ and a \f$size_t\f$ which contains the node's id. + /// The visitor should accept a reference to a value of type \emph{TypeT} and a \emph{size_t} which contains the node's id. /// The visitor should return one of the following values in the `fennec::traversal_control_` enum /// /// \tparam OrderT The order with which to traverse the tree. - /// \tparam VisitorT The visitor, should fulfill the signature \f$uint8_t visit(TypeT&, size_t)\f$ + /// \tparam VisitorT The visitor, should fulfill the signature \emph{uint8_t visit(TypeT&, size_t)} /// \param visit The visiting object /// \param i The node to start at /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// template constexpr void traverse(VisitorT&& visit, size_t i) { @@ -667,16 +667,16 @@ public: /// \brief Traverse the tree using a specified order and visiting functor /// /// \details - /// The visitor should accept a reference to a value of type \f$TypeT\f$ and a \f$size_t\f$ which contains the node's id. + /// The visitor should accept a reference to a value of type \emph{TypeT} and a \emph{size_t} which contains the node's id. /// The visitor should return one of the following values in the `fennec::traversal_control_` enum /// /// \tparam OrderT The order with which to traverse the tree. - /// \tparam VisitorT The visitor, should fulfill the signature \f$uint8_t visit(TypeT&, size_t)\f$ + /// \tparam VisitorT The visitor, should fulfill the signature \emph{uint8_t visit(TypeT&, size_t)} /// \param visit The visiting object /// \param i The node to start at /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// template constexpr void traverse(VisitorT&& visit, size_t i) const { @@ -717,9 +717,9 @@ public: return npos; } - size_t lft = tree.left(tree.parent(node)); - size_t nxt = lft == node ? tree.right(tree.parent(node)) : npos; - size_t chd = tree.left(node); + const size_t lft = tree.left(tree.parent(node)); + const size_t nxt = lft == node ? tree.right(tree.parent(node)) : npos; + const size_t chd = tree.left(node); if (nxt != npos && node != head) { visit.push_front(nxt); @@ -769,7 +769,7 @@ public: } size_t nxt = tree.right(tree.parent(node)); - size_t chd = tree.left(node); + const size_t chd = tree.left(node); nxt = node == nxt ? npos : nxt; if (nxt != npos && node != head) { @@ -792,7 +792,7 @@ public: private: list visit; - size_t head; + size_t head = { 0 }; }; /// @@ -819,9 +819,9 @@ public: return npos; } - size_t parent = tree.parent(node); - size_t pright = tree.right(parent); - size_t next = tree.left_most(tree.right(node)); + const size_t parent = tree.parent(node); + const size_t pright = tree.right(parent); + const size_t next = tree.left_most(tree.right(node)); if (node != pright && parent != npos) { visit.push_front(parent); @@ -843,7 +843,7 @@ public: private: list visit; - size_t head; + size_t head = { 0 }; }; /// @@ -870,15 +870,15 @@ public: return npos; } - size_t parent = tree.parent(node); - size_t pright = tree.right(parent); + const size_t parent = tree.parent(node); + const size_t right = tree.right(parent); - if (node == pright) { + if (node == right) { if (parent != npos) { visit.push_front(parent); } - } else if (pright != npos) { - visit.push_front(this->_successor(tree, pright)); + } else if (right != npos) { + visit.push_front(this->_successor(tree, right)); } if (not visit.is_empty()) { @@ -894,7 +894,7 @@ public: private: list visit; - size_t head; + size_t head = { 0 }; constexpr size_t _successor(const bintree& tree, size_t n) { size_t s = tree.left_most(n); @@ -919,7 +919,7 @@ public: /// @{ /// - /// \brief C++ Iterator Specification \f$iterator\f$ + /// \brief C++ Iterator Specification \emph{iterator} /// \details Performs pre-order traversal class iterator { @@ -954,7 +954,7 @@ public: /// /// \brief iterator pre-increment operator - /// \returns A reference to self after having stepped to the next node + /// \returns A reference to \emph{this} after having stepped to the next node iterator& operator++() { return _n = _order[*_tree, _n, traversal_control_continue], *this; } @@ -988,7 +988,7 @@ public: /// /// \brief iterator equality operator /// \param it the iterator to compare with - /// \returns \f$true\f$ if iterators are identical, \f$false\f$ otherwise + /// \returns \emph{true} if iterators are identical, \emph{false} otherwise constexpr bool operator==(const iterator& it) { return _tree == it._tree and _n == it._n; } @@ -996,7 +996,7 @@ public: /// /// \brief iterator inequality operator /// \param it the iterator to compare with - /// \returns \f$true\f$ if iterators are different, \f$false\f$ otherwise + /// \returns \emph{true} if iterators are different, \emph{false} otherwise constexpr bool operator!=(const iterator& it) { return _tree != it._tree or _n != it._n; } @@ -1009,7 +1009,7 @@ public: /// - /// \brief C++ Iterator Specification \f$iterator\f$ + /// \brief C++ Iterator Specification \emph{iterator} /// \details Performs pre-order traversal class const_iterator { @@ -1044,7 +1044,7 @@ public: /// /// \brief iterator pre-increment operator - /// \returns A reference to self after having stepped to the next node + /// \returns A reference to \emph{this} after having stepped to the next node const_iterator& operator++() { return _n = _order[*_tree, _n, traversal_control_continue], *this; } @@ -1064,7 +1064,7 @@ public: /// /// \brief iterator equality operator /// \param it the iterator to compare with - /// \returns \f$true\f$ if iterators are identical, \f$false\f$ otherwise + /// \returns \emph{true} if iterators are identical, \emph{false} otherwise constexpr bool operator==(const iterator& it) { return _tree == it._tree and _n == it._n; } @@ -1072,7 +1072,7 @@ public: /// /// \brief iterator inequality operator /// \param it the iterator to compare with - /// \returns \f$true\f$ if iterators are different, \f$false\f$ otherwise + /// \returns \emph{true} if iterators are different, \emph{false} otherwise constexpr bool operator!=(const iterator& it) { return _tree != it._tree or _n != it._n; } @@ -1087,18 +1087,18 @@ public: /// \returns an iterator at the first element in pre-order traversal /// /// \par Complexity - /// \f$O(\log N)\f$ + /// \emph{O(\log N)} /// iterator begin() { return iterator(this, _root); } /// - /// \brief C++ Iterator Specification \f$begin()\f$ + /// \brief C++ Iterator Specification \emph{begin()} /// \returns an iterator at the first element in pre-order traversal /// /// \par Complexity - /// \f$O(\log N)\f$ + /// \emph{O(\log N)} /// const_iterator begin() const { return iterator(this, _root); @@ -1108,18 +1108,18 @@ public: /// \returns an iterator at the first element in pre-order traversal /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// iterator end() { return iterator(this, _root, nullid); } /// - /// \brief C++ Iterator Specification \f$end()\f$ + /// \brief C++ Iterator Specification \emph{end()} /// \returns an iterator at the first element in pre-order traversal /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// const_iterator end() const { return iterator(this, _root, nullid); @@ -1228,8 +1228,8 @@ private: } constexpr size_t& _sibling(size_t i) { - size_t p = _parent(i); - bool d = i == _right(p); + const size_t p = _parent(i); + const bool d = i == _right(p); return _child(p, !d); } diff --git a/include/fennec/containers/bitfield.h b/include/fennec/containers/bitfield.h index 77e9385..d76a257 100644 --- a/include/fennec/containers/bitfield.h +++ b/include/fennec/containers/bitfield.h @@ -31,10 +31,11 @@ #ifndef FENNEC_CONTAINERS_BITFIELD_H #define FENNEC_CONTAINERS_BITFIELD_H -#include #include #include +#include + namespace fennec { @@ -42,20 +43,19 @@ namespace fennec /// \brief Bitfield Container with basic Bit Ops /// /// \details -/// | Property | Value | -/// |:-----------:|:----------:| -/// | stable | ⛔ | -/// | dynamic | ⛔ | -/// | homogeneous | ✅ | -/// | distinct | ⛔ | -/// | ordered | ⛔ | -/// | space | \f$O(N)\f$ | -/// | linear | ✅ | -/// | access | \f$O(1)\f$ | -/// | find | \f$O(N)\f$ | -/// | insertion | ⛔ | -/// | deletion | ⛔ | -/// | space | \f$O(N)\f$ | +/// | Property | Value | +/// |:-----------:|:-----------:| +/// | stable | ⛔ | +/// | dynamic | ⛔ | +/// | homogeneous | ✅ | +/// | distinct | ⛔ | +/// | ordered | ⛔ | +/// | linear | ✅ | +/// | space | \emph{O(N)} | +/// | access | \emph{O(1)} | +/// | find | \emph{O(N)} | +/// | insertion | ⛔ | +/// | deletion | ⛔ | /// /// \tparam N The number of bits in the bitfield template @@ -81,10 +81,10 @@ public: /// /// \brief Default constructor. - /// \details Initializes all bits with \f$0\f$. + /// \details Initializes all bits with \emph{0}. /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// constexpr bitfield() : _bytes() { @@ -93,10 +93,10 @@ public: /// /// \brief Boolean array constructor. /// \param arr An array of boolean values resembling each bit. - /// \details Initializes each bit with the respective boolean value in \f$arr\f$ + /// \details Initializes each bit with the respective boolean value in \emph{arr} /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// explicit constexpr bitfield(const bool (&arr)[N]) : _bytes() { @@ -108,10 +108,10 @@ public: /// /// \brief Index array constructor. /// \param arr An array of indices. - /// \details Sets the bits of each index provided in \f$arr\f$. + /// \details Sets the bits of each index provided in \emph{arr}. /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// template explicit constexpr bitfield(const size_t (&arr)[I]) @@ -123,11 +123,11 @@ public: /// /// \param args A set of indices. - /// \details This substitution assumes \f$ArgsT\ldots\f$ can be taken as an array of indices.
- /// Sets the bits of each index provided in \f$args\ldots\f$. + /// \details This substitution assumes \emph{ArgsT...} can be taken as an array of indices.
+ /// Sets the bits of each index provided in \emph{args...}. /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// template constexpr bitfield(ArgsT&&...args) @@ -138,12 +138,12 @@ public: /// /// \brief Variadic array constructor /// \param args A set of boolean values. - /// \details This substitution assumes \f$ArgsT\ldots\f$ can be taken as an array of booleans.
- /// Initializes each bit with the respective boolean in \f$args\ldots\f$.
+ /// \details This substitution assumes \emph{ArgsT...} can be taken as an array of booleans.
+ /// Initializes each bit with the respective boolean in \emph{args...}.
/// Does not necessitate the number of arguments be equal to the number of bits. /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// template requires((is_bool_v or is_convertible_v) and ...) constexpr bitfield(ArgsT&&...args) @@ -157,7 +157,7 @@ public: /// \param bf bitfield to copy /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// bitfield(const bitfield& bf) : _bytes(bf._bytes) { @@ -168,7 +168,7 @@ public: /// \param bf bitfield to move /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// bitfield(bitfield&& bf) noexcept : _bytes(bf._bytes) { @@ -190,20 +190,20 @@ public: /// /// \brief copy assignment /// \param bf bitfield to copy - /// \returns a reference to self + /// \returns a reference to \emph{this} /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// bitfield& operator=(const bitfield& bf) = default; /// /// \brief move assignment /// \param bf bitfield to move - /// \returns a reference to self + /// \returns a reference to \emph{this} /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// bitfield& operator=(bitfield&& bf) noexcept = default; @@ -222,12 +222,12 @@ public: /// \returns the value stored in the bit as a boolean /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// bool test(size_t i) const { assertd(i < bits, "Index out of Bounds!"); size_t b = i / 8; - size_t o = i % 8; + const size_t o = i % 8; return _bytes[b] & (1 << o); } @@ -236,12 +236,12 @@ public: /// \param i the index of the bit /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// void set(size_t i) { assertd(i < bits, "Index out of Bounds!"); size_t b = i / 8; - size_t o = i % 8; + const size_t o = i % 8; _bytes[b] |= (1 << o); } @@ -250,12 +250,12 @@ public: /// \param i the index of the bit /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// void clear(size_t i) { assertd(i < bits, "Index out of Bounds!"); size_t b = i / 8; - size_t o = i % 8; + const size_t o = i % 8; _bytes[b] &= ~(1 << o); } @@ -264,27 +264,27 @@ public: /// \param i the index of the bit /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// void toggle(size_t i) { assertd(i < bits, "Index out of Bounds!"); size_t b = i / 8; - size_t o = i % 8; + const size_t o = i % 8; _bytes[b] ^= (1 << o); } /// - /// \brief store \f$v\f$ in bit \f$i\f$ + /// \brief store \emph{v} in bit \emph{i} /// \param i the index of the bit /// \param v the value to store /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// void store(size_t i, bool v) { assertd(i < bits, "Index out of Bounds!"); size_t b = i / 8; - size_t o = i % 8; + const size_t o = i % 8; (_bytes[b] &= ~((1 << o))) |= ((v << o)); } @@ -293,7 +293,7 @@ public: /// \returns a bitfield containing the bit-wise inverse /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// bitfield operator~() const { bitfield res = *this; diff --git a/include/fennec/containers/containers.h b/include/fennec/containers/containers.h index f1e0a8f..15f71bf 100644 --- a/include/fennec/containers/containers.h +++ b/include/fennec/containers/containers.h @@ -42,20 +42,19 @@ /// /// \section fennec_containers_container_section_properties Container Properties /// -/// | Property | Meaning | -/// |:----------------|:-----------------------------------------------------------------------------------------------| -/// | **stable** | Any pointer reference to an element remains constant for the lifetime of the container. | -/// | **dynamic** | Memory for this container is allocated on the heap. | -/// | **homogeneous** | The types of all elements are either identical, or inherit the same base type. | -/// | **distinct** | Elements are guaranteed to be unique in their value. | -/// | **ordered** | Elements are guaranteed to be in order, such that for any index \f$i\f$, \f$E_i < E_{i + 1}\f$ | -/// | **space** | The amount of memory allocated with respect to the number of elements, in big-O notation. | -/// | **linear** | Each element is sequential in terms of access. | -/// | **access** | The runtime of the access operators and functions, in big-O notation. | -/// | **find** | The runtime of finding an element in the container, in big-O notation. | -/// | **insertion** | The runtime of inserting an element in the container, in big-O notation. | -/// | **deletion** | The runtime of erasing an element in the container, in big-O notation. | -/// | **space** | The space complexity of the container. | +/// | Property | Meaning | +/// |:----------------|:-------------------------------------------------------------------------------------------------------------------| +/// | **stable** | Any pointer reference to an element remains constant for the lifetime of the container. | +/// | **dynamic** | Memory for this container is allocated on the heap. | +/// | **homogeneous** | The types of all elements are either identical, or inherit the same base type. | +/// | **distinct** | Elements are guaranteed to be unique in their value. | +/// | **ordered** | Elements are guaranteed to be in order, such that for any index \math{i}, \math{\textbf{E}_i < \textbf{E}_{i + 1}} | +/// | **space** | The amount of memory allocated with respect to the number of elements, in big-O notation. | +/// | **linear** | Each element is sequential in terms of access. | +/// | **access** | The runtime of the access operators and functions, in big-O notation. | +/// | **find** | The runtime of finding an element in the container, in big-O notation. | +/// | **insertion** | The runtime of inserting an element in the container, in big-O notation. | +/// | **deletion** | The runtime of erasing an element in the container, in big-O notation. | /// /// /// \section fennec_containers_section_cppstdlib C++ Standard Template Library diff --git a/include/fennec/containers/deque.h b/include/fennec/containers/deque.h index 41870bb..cbc3707 100644 --- a/include/fennec/containers/deque.h +++ b/include/fennec/containers/deque.h @@ -33,8 +33,6 @@ #include -// TODO: Document - namespace fennec { @@ -46,20 +44,19 @@ namespace fennec /// This behaves the similar to fennec::list, however it does not allow arbitrary access, insertion, or deletion. /// It is one of the few data structures in this library that is stable, i.e. pointers to elements do not change. /// -/// | Property | Value | -/// |:-----------:|:----------:| -/// | stable | ✅ | -/// | dynamic | ✅ | -/// | homogeneous | ✅ | -/// | distinct | ⛔ | -/// | ordered | ⛔ | -/// | space | \f$O(N)\f$ | -/// | linear | ⛔ | -/// | access | \f$O(1)\f$ | -/// | find | \f$O(N)\f$ | -/// | insertion | \f$O(1)\f$ | -/// | deletion | \f$O(1)\f$ | -/// | space | \f$O(N)\f$ | +/// | Property | Value | +/// |:-----------:|:-----------:| +/// | stable | ✅ | +/// | dynamic | ✅ | +/// | homogeneous | ✅ | +/// | distinct | ⛔ | +/// | ordered | ⛔ | +/// | linear | ⛔ | +/// | space | \emph{O(N)} | +/// | access | \emph{O(1)} | +/// | find | \emph{O(N)} | +/// | insertion | \emph{O(1)} | +/// | deletion | \emph{O(1)} | /// /// \tparam TypeT value type template> @@ -93,7 +90,7 @@ public: /// \brief Default Constructor, initializes an empty deque /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// deque() : _alloc() @@ -107,7 +104,7 @@ public: /// \param alloc the allocator to copy /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// deque(const alloc_t& alloc) : _alloc(alloc) @@ -121,7 +118,7 @@ public: /// \param deque the deque to copy /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// deque(const deque& deque) : _alloc(deque._alloc) @@ -140,7 +137,7 @@ public: /// \param deque the deque to move /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// deque(deque&& deque) noexcept : _alloc(deque._alloc) @@ -155,7 +152,7 @@ public: /// \brief Destructor, calls deque::clear /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// ~deque() { clear(); @@ -169,10 +166,10 @@ public: /// @{ /// - /// \returns \f$true\f$ when the deque is empty, \f$false\f$ otherwise + /// \returns \emph{true} when the deque is empty, \emph{false} otherwise /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr bool is_empty() const { return _size == 0; @@ -182,7 +179,7 @@ public: /// \returns the number of elements in the deque /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr size_t size() const { return _size; @@ -200,7 +197,7 @@ public: /// \returns a reference to the first element in the deque /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// value_t& front() { assert(not is_empty(), "Attempted to access an empty deque."); @@ -211,7 +208,7 @@ public: /// \returns a const-qualified reference to the first element in the deque /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// const value_t& front() const { assert(not is_empty(), "Attempted to access an empty deque."); @@ -222,7 +219,7 @@ public: /// \returns a reference to the last element in the deque /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// value_t& back() { assert(not is_empty(), "Attempted to access an empty deque."); @@ -233,7 +230,7 @@ public: /// \returns a const-qualified reference to the last element in the deque /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// const value_t& back() const { assert(not is_empty(), "Attempted to access an empty deque."); @@ -253,7 +250,7 @@ public: /// \param elem the value to move /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// void push_front(value_t&& elem) { this->_push_front(elem); @@ -264,7 +261,7 @@ public: /// \param elem the value to copy /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// void push_front(const value_t& elem) { this->_push_front(elem); @@ -276,7 +273,7 @@ public: /// \param args Arguments used to construct the value /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// template void emplace_front(ArgsT&&...args) { @@ -289,7 +286,7 @@ public: /// \param elem the value to move /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// void push_back(value_t&& elem) { this->_push_back(elem); @@ -300,7 +297,7 @@ public: /// \param elem the value to copy /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// void push_back(const value_t& elem) { this->_push_back(elem); @@ -312,7 +309,7 @@ public: /// \param args Arguments used to construct the value /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// template void emplace_back(ArgsT&&...args) { @@ -323,7 +320,7 @@ public: /// \brief Clears the contents of the deque /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// void clear() { elem_t it = _first; @@ -342,7 +339,7 @@ public: /// \brief Erase the First Element /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// void pop_front() { if (_first == nullptr) { @@ -360,7 +357,7 @@ public: /// \brief Erase the Last Element /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// void pop_back() { if (_last == nullptr) { diff --git a/include/fennec/containers/detail/_tuple.h b/include/fennec/containers/detail/_tuple.h index 73616cd..72f7c0d 100644 --- a/include/fennec/containers/detail/_tuple.h +++ b/include/fennec/containers/detail/_tuple.h @@ -18,6 +18,7 @@ #ifndef FENNEC_CONTAINERS_DETAIL_TUPLE_H #define FENNEC_CONTAINERS_DETAIL_TUPLE_H + #include #include @@ -28,8 +29,11 @@ namespace fennec::detail template struct _tuple_leaf { - template - constexpr _tuple_leaf(ArgT&& arg) : value(fennec::forward(arg)) {} + constexpr _tuple_leaf(_tuple_leaf&&) noexcept = default; + constexpr _tuple_leaf(const _tuple_leaf&) = default; + + template requires(not is_same_v, _tuple_leaf>) + constexpr explicit _tuple_leaf(ArgT&& arg) : value(fennec::forward(arg)) {} constexpr ~_tuple_leaf() = default; @@ -45,8 +49,11 @@ struct _tuple; template struct _tuple, TypesT...> : _tuple_leaf... { + constexpr _tuple(_tuple&&) noexcept = default; + constexpr _tuple(const _tuple&) = default; + template - constexpr _tuple(ArgsT&&... args) + constexpr explicit _tuple(ArgsT&&... args) : _tuple_leaf(fennec::forward(args))... { } diff --git a/include/fennec/containers/dynarray.h b/include/fennec/containers/dynarray.h index 8753697..9558de1 100644 --- a/include/fennec/containers/dynarray.h +++ b/include/fennec/containers/dynarray.h @@ -31,10 +31,13 @@ #ifndef FENNEC_CONTAINERS_DYNARRAY_H #define FENNEC_CONTAINERS_DYNARRAY_H -#include #include + #include -#include + +#include + +#include namespace fennec { @@ -43,20 +46,19 @@ namespace fennec /// /// \brief Wrapper for dynamically sized and allocated arrays /// \details -/// | Property | Value | -/// |:-----------:|:----------:| -/// | stable | ⛔ | -/// | dynamic | ✅ | -/// | homogeneous | ✅ | -/// | distinct | ⛔ | -/// | ordered | ⛔ | -/// | space | \f$O(N)\f$ | -/// | linear | ✅ | -/// | access | \f$O(1)\f$ | -/// | find | \f$O(N)\f$ | -/// | insertion | \f$O(N)\f$ | -/// | deletion | \f$O(N)\f$ | -/// | space | \f$O(N)\f$ | +/// | Property | Value | +/// |:-----------:|:-----------:| +/// | stable | ⛔ | +/// | dynamic | ✅ | +/// | homogeneous | ✅ | +/// | distinct | ⛔ | +/// | ordered | ⛔ | +/// | linear | ✅ | +/// | space | \emph{O(N)} | +/// | access | \emph{O(1)} | +/// | find | \emph{O(N)} | +/// | insertion | \emph{O(N)} | +/// | deletion | \emph{O(N)} | /// /// This structure prefers shallow moves and deep copies. /// @@ -86,7 +88,7 @@ public: /// \brief Default Constructor, initializes an empty allocation. /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr dynarray() : _alloc(8) @@ -99,7 +101,7 @@ public: /// data. /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// explicit constexpr dynarray(const alloc_t& alloc) : _alloc(8, alloc) @@ -107,11 +109,11 @@ public: } /// - /// \brief Sized Allocation, initializes a dynarray with \f$n\f$ elements using the default constructor. + /// \brief Sized Allocation, initializes a dynarray with \emph{n} elements using the default constructor. /// \param n The number of elements. /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// explicit constexpr dynarray(size_t n) : _alloc(n) @@ -124,13 +126,13 @@ public: } /// - /// \brief Sized Allocation Alloc Constructor, initializes a dynarray with allocator \f$alloc\f$ and \f$n\f$ elements + /// \brief Sized Allocation Alloc Constructor, initializes a dynarray with allocator \emph{alloc} and \emph{n} elements /// using the default constructor. /// \param n The number of elements /// \param alloc The allocator object to copy /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// constexpr dynarray(size_t n, const alloc_t& alloc) : _alloc(n, alloc) @@ -142,13 +144,13 @@ public: } /// - /// \brief Sized Allocation Copy Constructor, Create an allocation of size \f$n\f$ elements, with each element + /// \brief Sized Allocation Copy Constructor, Create an allocation of size \emph{n} elements, with each element /// constructed using the copy constructor /// \param n the number of elements /// \param val the value to copy /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// constexpr dynarray(size_t n, const TypeT& val) : _alloc(n) @@ -166,7 +168,7 @@ public: /// \param args The arguments to create each object with /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// template constexpr explicit dynarray(size_t n, ArgsT&&...args) @@ -183,7 +185,7 @@ public: /// \param arr The array to copy /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// template constexpr dynarray(const TypeT (&arr)[N]) @@ -200,7 +202,7 @@ public: /// \param arr The array to move /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// template constexpr dynarray(TypeT (&&arr)[N]) @@ -212,13 +214,13 @@ public: } /// - /// \brief Conversion Constructor, copies elements of conv as this \f$value_t\f$ + /// \brief Conversion Constructor, copies elements of conv as this \emph{value_t} /// \tparam OTypeT The other value type /// \tparam OAlloc The other allocator type /// \param conv The dynarray to convert /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// template constexpr dynarray(const dynarray& conv) @@ -236,7 +238,7 @@ public: /// \param alloc An allocator object to copy /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// constexpr dynarray(initializer_list l, const alloc_t& alloc = alloc_t()) : _alloc(l.size(), alloc) @@ -252,7 +254,7 @@ public: /// \param arr the dynarray to copy /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// constexpr dynarray(const dynarray& arr) : _alloc(arr._size) @@ -267,7 +269,7 @@ public: /// \param arr the dynarray to move /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr dynarray(dynarray&& arr) noexcept : _alloc(fennec::move(arr._alloc)) @@ -279,7 +281,7 @@ public: /// \brief Default Destructor, destructs all elements and frees the underlying allocation /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// constexpr ~dynarray() { value_t* addr = _alloc.data(); @@ -292,10 +294,6 @@ public: /// @} -private: - // This constructor should not be invokable since moving is a single object operation and will cause undefined - // behaviour when moving to multiple elements - constexpr dynarray(size_t n, TypeT&& val) = delete; // Assignment ========================================================================================================== @@ -307,10 +305,10 @@ public: /// /// \brief Copy Assignment Operator /// \param arr the array to copy - /// \returns A dynarray after having copied each element of \f$arr\f$ + /// \returns A dynarray after having copied each element of \emph{arr} /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// constexpr dynarray& operator=(const dynarray& arr) { this->clear(); @@ -324,10 +322,10 @@ public: /// /// \brief Move Assignment Operator /// \param arr the array to move - /// \returns A dynarray after having taken ownership of the contents of \f$arr\f$ + /// \returns A dynarray after having taken ownership of the contents of \emph{arr} /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr dynarray& operator=(dynarray&& arr) noexcept { this->clear(); @@ -341,10 +339,10 @@ public: /// \brief Array Copy Assignment Operator /// \tparam N the length of the array /// \param arr the array to copy - /// \returns A dynarray after having copied each element of \f$arr\f$ + /// \returns A dynarray after having copied each element of \emph{arr} /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// template constexpr dynarray& operator=(const TypeT (&arr)[N]) { @@ -360,10 +358,10 @@ public: /// \brief Array Copy Assignment Operator /// \tparam N the length of the array /// \param arr the array to copy - /// \returns A dynarray after having moved each element of \f$arr\f$ + /// \returns A dynarray after having moved each element of \emph{arr} /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// template constexpr dynarray& operator=(TypeT (&&arr)[N]) { @@ -387,7 +385,7 @@ public: /// \returns The size of the dynarray in elements /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr size_t size() const { return _size; @@ -397,7 +395,7 @@ public: /// \returns The current capacity, in elements, of the underlying allocation /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr size_t capacity() const { return _alloc.capacity(); @@ -407,7 +405,7 @@ public: /// \returns True when there are no elements active, otherwise false /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr bool is_empty() const { return _size == 0; @@ -425,10 +423,10 @@ public: /// /// \brief Array Access Operator /// \param i The index to access - /// \returns A reference to the element at index \f$i\f$ + /// \returns A reference to the element at index \emph{i} /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr TypeT& operator[](size_t i) { assertd(i < _size, "Array Out of Bounds"); @@ -438,10 +436,10 @@ public: /// /// \brief Array Access Operator (const) /// \param i The index to access - /// \returns A const qualified reference to the element at index \f$i\f$ + /// \returns A const qualified reference to the element at index \emph{i} /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr const TypeT& operator[](size_t i) const { assertd(i < _size, "Array Out of Bounds"); @@ -452,7 +450,7 @@ public: /// \returns Reference to the first element in the dynarray /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr TypeT& front() { return this->operator[](0); @@ -462,7 +460,7 @@ public: /// \returns A const-qualified reference to the first element in the dynarray /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr const TypeT& front() const { return this->operator[](0); @@ -472,7 +470,7 @@ public: /// \returns A reference to the last element in the dynarray /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr TypeT& back() { return this->operator[](size() - 1); @@ -482,7 +480,7 @@ public: /// \returns A const-qualified reference to the last element in the dynarray /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr const TypeT& back() const { return this->operator[](size() - 1); @@ -492,7 +490,7 @@ public: /// \returns A pointer to the underlying allocation /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr TypeT* data() { return _alloc.data(); @@ -502,7 +500,7 @@ public: /// \returns A pointer to the underlying allocation /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr const TypeT* data() const { return _alloc.data(); @@ -523,7 +521,7 @@ public: /// \param val the value to initialize with /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// constexpr void insert(size_t i, TypeT&& val) { @@ -535,8 +533,8 @@ public: // Move the data if we are not inserting at the end of the array if((i = min(i, _size)) < _size) { fennec::memmove( - (void*)(_alloc.data() + i + 1) - , (void*)(_alloc.data() + i) + static_cast(_alloc.data() + i + 1) + , static_cast(_alloc.data() + i) , (_size - i) * sizeof(TypeT)); } @@ -551,7 +549,7 @@ public: /// \param val the value to initialize with /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// constexpr void insert(size_t i, const TypeT& val) { @@ -563,8 +561,8 @@ public: // Move the data if we are not inserting at the end of the array if((i = min(i, _size)) < _size) { fennec::memmove( - (void*)(_alloc.data() + i), - (void*)(_alloc.data() + i + 1), + static_cast(_alloc.data() + i), + static_cast(_alloc.data() + i + 1), (_size - i) * sizeof(TypeT) ); } @@ -581,7 +579,7 @@ public: /// \tparam ArgsT Argument types /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// template constexpr void emplace(size_t i, ArgsT&&...args) { @@ -594,8 +592,8 @@ public: // Move the data if we are not inserting at the end of the array if((i = min(i, _size)) < _size) { fennec::memmove( - (void*)(_alloc.data() + i) - , (void*)(_alloc.data() + i + 1) + static_cast(_alloc.data() + i) + , static_cast(_alloc.data() + i + 1) , (_size - i) * sizeof(TypeT)); } @@ -609,7 +607,7 @@ public: /// \param val Value to initialize with /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr void push_back(const TypeT& val) { dynarray::insert(_size, val); @@ -620,7 +618,7 @@ public: /// \param val Value to initialize with /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr void push_back(TypeT&& val) { dynarray::insert(_size, fennec::forward(val)); @@ -632,7 +630,7 @@ public: /// \param args Arguments to construct with /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// template constexpr void emplace_back(ArgsT...args) { @@ -643,7 +641,7 @@ public: /// \brief Erase last element /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr void pop_back() { fennec::destruct(&_alloc[--_size]); @@ -653,10 +651,10 @@ public: /// \brief Resize the dynarray, invoking the default constructor for all new elements /// \param n The new size in elements /// - /// \details if \f$n\f$ is less than the current size, any elements that would be removed are destructed + /// \details if \emph{n} is less than the current size, any elements that would be removed are destructed /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// constexpr void resize(size_t n) { _reduce(n); @@ -674,10 +672,10 @@ public: /// \param n The new size in elements /// \param val The value to fill with /// - /// \details if \f$n\f$ is less than the current size, any elements that would be removed are destructed + /// \details if \emph{n} is less than the current size, any elements that would be removed are destructed /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// constexpr void resize(size_t n, const TypeT& val) { _reduce(n); @@ -694,10 +692,10 @@ public: /// \brief Reserve the array, allocating new space without initialization /// \param n The new capacity in elements /// - /// \details if \f$n\f$ is less than the current size, any elements that would be removed are destructed + /// \details if \emph{n} is less than the current size, any elements that would be removed are destructed /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// constexpr void reserve(size_t n) { _reduce(n); @@ -708,7 +706,7 @@ public: /// \brief Clears the contents of the dynarray, destructing all elements and releasing the allocation. /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// constexpr void clear() { _reduce(0); @@ -728,16 +726,16 @@ public: /// \returns A pointer to the first element in the dynarray /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr TypeT* begin() { return _alloc; } /// - /// \brief C++ Iterator Specification \f$begin()\f$ + /// \brief C++ Iterator Specification \emph{begin()} /// \returns A const qualified pointer to the first element in the dynarray /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr const TypeT* begin() const { return _alloc; } @@ -746,16 +744,16 @@ public: /// \return A pointer to the address after the last element in the dynarray /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr TypeT* end() { return begin() + _size; } /// - /// \brief C++ Iterator Specification \f$end()\f$ + /// \brief C++ Iterator Specification \emph{end()} /// \return A const qualified pointer to the address after the last element in the dynarray /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr const TypeT* end() const { return begin() + _size; } @@ -783,6 +781,27 @@ private: } }; +/// +/// \brief Formatter for `fennec::dynarray` +/// \tparam T The element type. +template +struct formatter> { + /// + /// \brief format function + /// \param str the string argument + /// \returns the formatted version of \emph{str} + string operator()(const format_arg& fmt, const dynarray& arr) const { + string res = string("[ "); + for (auto& it : arr) { + res += ' '; + res += base(fmt, it); + } + return res; + } + + static constexpr formatter base = {}; +}; + } #endif // FENNEC_CONTAINERS_DYNARRAY_H diff --git a/include/fennec/containers/generic.h b/include/fennec/containers/generic.h index ad55500..046c3cf 100644 --- a/include/fennec/containers/generic.h +++ b/include/fennec/containers/generic.h @@ -32,6 +32,7 @@ #define FENNEC_CONTAINERS_GENERIC_H #include + #include namespace fennec @@ -40,20 +41,19 @@ namespace fennec /// /// \brief A struct capable of holding a single object of any type /// \details -/// | Property | Value | -/// |:-----------:|:----------:| -/// | stable | ✅ | -/// | dynamic | ⛔ | -/// | homogeneous | ⛔ | -/// | distinct | ⛔ | -/// | ordered | ⛔ | -/// | space | \f$O(1)\f$ | -/// | linear | ✅ | -/// | access | \f$O(1)\f$ | -/// | find | ⛔ | -/// | insertion | \f$O(1)\f$ | -/// | deletion | \f$O(1)\f$ | -/// | space | \f$O(1)\f$ | +/// | Property | Value | +/// |:-----------:|:-----------:| +/// | stable | ✅ | +/// | dynamic | ⛔ | +/// | homogeneous | ⛔ | +/// | distinct | ⛔ | +/// | ordered | ⛔ | +/// | linear | ✅ | +/// | space | \emph{O(1)} | +/// | access | \emph{O(1)} | +/// | find | ⛔ | +/// | insertion | \emph{O(1)} | +/// | deletion | \emph{O(1)} | struct generic { // Definitions ========================================================================================================= @@ -79,7 +79,7 @@ public: /// \brief Default Constructor /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// generic() : _handle(nullptr) @@ -91,7 +91,7 @@ public: /// \param gen The generic object to copy /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// generic(const generic& gen) : _handle(nullptr) @@ -106,7 +106,7 @@ public: /// \param gen The generic object to move /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// generic(generic&& gen) : _handle(gen._handle) @@ -121,7 +121,7 @@ public: /// \param x The value /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// template generic(T&& x) @@ -136,7 +136,7 @@ public: /// \param args The argument values /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// template generic(type_identity, ArgsT&&...args) @@ -164,17 +164,17 @@ public: /// \returns a runtime type struct referencing the held type /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// type type() const { return *static_cast(_manage(op_type, nullptr)); } /// - /// \returns \f$true\f$ if there is a held value, \f$false\f$ otherwise + /// \returns \emph{true} if there is a held value, \emph{false} otherwise /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// bool has_value() const { return _handle != nullptr; @@ -192,10 +192,10 @@ public: /// /// \brief copy assignment /// \param gen the generic to copy - /// \returns a reference to self after copying the contents of \f$gen\f$ + /// \returns a reference to \emph{this} after copying the contents of \emph{gen} /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// generic& operator=(const generic& gen) { if (this == &gen) { // self-assignment case @@ -211,10 +211,10 @@ public: /// /// \brief move assignment /// \param gen the generic to move - /// \returns a reference to self after swapping contents with \f$gen\f$ + /// \returns a reference to \emph{this} after swapping contents with \emph{gen} /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// generic& operator=(generic&& gen) noexcept { swap(gen); @@ -225,10 +225,10 @@ public: /// \brief value assignment /// \tparam T the type of the value /// \param x the value to assign - /// \returns a reference to self after having assigned \f$x\f$ + /// \returns a reference to \emph{this} after having assigned \emph{x} /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// template generic& operator=(T&& x) { @@ -250,13 +250,13 @@ public: /// /// \brief emplace value /// - /// \details constructs a new value of type \f$T\f$ using \f$args\ldots\f$ + /// \details constructs a new value of type \emph{T} using \emph{args\ldots} /// \tparam T the type to construct /// \tparam ArgsT the argument types /// \param args the argument values /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// template void emplace(ArgsT&&...args) { @@ -270,7 +270,7 @@ public: /// \details clears the held value using the appropriate destructor /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// void reset() { if (_manage) { @@ -284,7 +284,7 @@ public: /// \param gen the generic to swap with /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// void swap(generic& gen) noexcept { fennec::swap(_handle, gen._handle); @@ -303,12 +303,12 @@ public: /// /// \brief cast value /// - /// \details equivalent to \f$reinterpret_cast\f$ + /// \details equivalent to \emph{reinterpret_cast} /// \tparam T The type to cast to - /// \returns The contents of generic after having cast to \f$T\f$ + /// \returns The contents of generic after having cast to \emph{T} /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// template> T cast() { @@ -316,12 +316,12 @@ public: } /// - /// \details equivalent to \f$reinterpret_cast\f$ + /// \details equivalent to \emph{reinterpret_cast} /// \tparam T The type to cast to - /// \returns The contents of generic after having cast to \f$T\f$ + /// \returns The contents of generic after having cast to \emph{T} /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// template> T cast() const { diff --git a/include/fennec/containers/graph.h b/include/fennec/containers/graph.h index d9f87f3..95ab0d4 100644 --- a/include/fennec/containers/graph.h +++ b/include/fennec/containers/graph.h @@ -35,7 +35,6 @@ #include #include #include -#include /* * With the directed tree we were able to cheat a little, the structure has more rules to it which allows @@ -55,20 +54,19 @@ namespace fennec /// \brief Graph Data Structure, describes sets of arbitrarily connected vertices /// /// \details -/// | Property | Value | -/// |:-----------:|:--------------:| -/// | stable | ⛔ | -/// | dynamic | ✅ | -/// | homogeneous | ✅ | -/// | distinct | ⛔ | -/// | ordered | ⛔ | -/// | space | \f$O(N)\f$ | -/// | linear | ✅ | -/// | access | \f$O(1)\f$ | -/// | find | \f$O(1)\f$ | -/// | insertion | \f$O(1)\f$ | -/// | deletion | \f$O(M)\f$ | -/// | space | \f$O(N + M)\f$ | +/// | Property | Value | +/// |:-----------:|:---------------:| +/// | stable | ⛔ | +/// | dynamic | ✅ | +/// | homogeneous | ✅ | +/// | distinct | ⛔ | +/// | ordered | ⛔ | +/// | linear | ✅ | +/// | space | \emph{O(N + M)} | +/// | access | \emph{O(1)} | +/// | find | \emph{O(1)} | +/// | insertion | \emph{O(1)} | +/// | deletion | \emph{O(M)} | /// /// Graphs contain vertices and edges. Graphs are either directed /// or undirected. This structure allows the creation of both directed and undirected edges. As @@ -80,11 +78,11 @@ namespace fennec /// A directed graph is weakly connected if replacing all of its directed edges with undirected edges would /// produce a connected graph. We will call this "disjointed" /// -/// A directed graph is semi-connected if there is a directed path p for \f$u\f$ → \f$v\f$ *or* \f$v\f$ → \f$u\f$ for every -/// pair of vertices \f$[u, v]\f$. We will call this "unilateral" +/// A directed graph is semi-connected if there is a directed path p for \emph{u} → \emph{v} *or* \emph{v} → \emph{u} for every +/// pair of vertices \emph{[u, v]}. We will call this "unilateral" /// -/// A directed graph is strongly-connected if there is a directed path p for \f$u\f$ → \f$v\f$ *and* \f$v\f$ → \f$u\f$ for every pair -/// of vertices \f$[u, v]\f$. We will call this "connected" +/// A directed graph is strongly-connected if there is a directed path p for \emph{u} → \emph{v} *and* \emph{v} → \emph{u} for every pair +/// of vertices \emph{[u, v]}. We will call this "connected" /// /// \tparam VertexT The type associated with each vertex /// \tparam EdgeT The type associated with each edge @@ -122,7 +120,7 @@ public: /// \brief Default Constructor, initializes empty graph /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr graph() = default; @@ -130,7 +128,7 @@ public: /// \brief Destructor /// /// \par Complexity - /// \f$O(N + M)\f$ + /// \math{\textbf{O(N} + \textbf{M)}} /// constexpr ~graph() = default; @@ -146,7 +144,7 @@ public: /// \returns A reference to this after assigning g /// /// \par Complexity - /// \f$O(N + M)\f$ + /// \math{\textbf{O(N} + \textbf{M)}} /// constexpr graph& operator=(const graph& g) = default; @@ -156,7 +154,7 @@ public: /// \returns A reference to this after assigning g /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr graph& operator=(graph&& g) = default; @@ -172,7 +170,7 @@ public: /// \returns The number of vertices in the graph /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr size_t num_vertices() const { return _vertex_pool.size(); @@ -182,7 +180,7 @@ public: /// \returns The number of edges in the graph /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr size_t num_edges() const { return _edge_pool.size(); @@ -192,57 +190,57 @@ public: /// \returns The capacity of the vertex pool /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr size_t capacity() const { return _vertex_pool.capacity(); } /// - /// \returns \f$true\f$ when there are no vertices in the graph, \f$false\f$ otherwise + /// \returns \emph{true} when there are no vertices in the graph, \emph{false} otherwise /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr bool is_empty() const { return num_vertices() == 0; } /// - /// \brief Checks if there exists an edge \f$e\f$ that starts from \f$a\f$ and ends at \f$b\f$ + /// \brief Checks if there exists an edge \math{e} that starts from \emph{a} and ends at \emph{b} /// \param a The first vertex /// \param b The second vertex - /// \returns \f$true\f$ if the edge exists, \f$false\f$ otherwise + /// \returns \emph{true} if the edge exists, \emph{false} otherwise /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr bool exists(size_t a, size_t b) const { return _edge_map[a][b] != nullptr; } /// - /// \brief Checks if there exists an edge \f$e0\f$ that starts from \f$a\f$ and ends at \f$b\f$ and \f$e1\f$ that starts from \f$b\f$ - /// and ends at \f$a\f$ + /// \brief Checks if there exists an edge \math{e_0} that starts from \emph{a} and ends at \emph{b} and \math{e_1} that starts from \emph{b} + /// and ends at \emph{a} /// \param a The first vertex /// \param b The second vertex - /// \returns \f$true\f$ if both edges exist, \f$false\f$ otherwise + /// \returns \emph{true} if both edges exist, \emph{false} otherwise /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr bool is_symmetric(size_t a, size_t b) const { return exists(a, b) and exists(b, a); } /// - /// \brief Checks if there exists an edge \f$e\f$ between \f$a\f$ and \f$b\f$ + /// \brief Checks if there exists an edge \math{e} between \emph{a} and \emph{b} /// \param a The first vertex /// \param b The second vertex - /// \returns \f$true\f$ if both edges exist, \f$false\f$ otherwise + /// \returns \emph{true} if both edges exist, \emph{false} otherwise /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr bool is_undirected(size_t a, size_t b) const { const auto* e0 = _edge_map[a][b]; @@ -269,7 +267,7 @@ public: /// \returns A reference to the value stored in the vertex /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr vertex_t& operator[](size_t vertex) { return _vertex_pool[vertex]; @@ -281,7 +279,7 @@ public: /// \returns A reference to the value stored in the vertex /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr const vertex_t& operator[](size_t vertex) const { return _vertex_pool[vertex]; @@ -291,10 +289,10 @@ public: /// \brief edge Access Operator /// \param a The id of the first vertex /// \param b The id of the second vertex - /// \returns A pointer to the value stored in the edge, \f$nullptr\f$ if not found + /// \returns A pointer to the value stored in the edge, \emph{nullptr} if not found /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr edge_t* operator[](size_t a, size_t b) { if (is_empty()) { @@ -311,10 +309,10 @@ public: /// \brief edge Const Access Operator /// \param a The id of the first vertex /// \param b The id of the second vertex - /// \returns A const-qualified pointer to the value stored in the edge, \f$nullptr\f$ if not found + /// \returns A const-qualified pointer to the value stored in the edge, \emph{nullptr} if not found /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr const edge_t* operator[](size_t a, size_t b) const { if (is_empty()) { @@ -328,12 +326,12 @@ public: } /// - /// \brief Getter for a list of vertices \f$x\f$ that \f$vertex\f$ has an edge to \f$x\ldots\f$ + /// \brief Getter for a list of vertices \emph{X} that \emph{vertex} has an edge to \emph{X...} /// \param vertex The id of the vertex - /// \returns A list containing all vertices \f$x\f$ with edges from \f$vertex\f$ to \f$x\ldots\f$ + /// \returns A list containing all vertices \emph{X} with edges from \emph{vertex} to \emph{X...} /// /// \par Complexity - /// \f$O(M)\f$ + /// \emph{O(M)} /// list outgoing(size_t vertex) { list res; @@ -347,12 +345,12 @@ public: } /// - /// \brief Getter for a list of vertices \f$x\f$ that \f$vertex\f$ has an edge from \f$x\ldots\f$ + /// \brief Getter for a list of vertices \emph{X} that \emph{vertex} has an edge from \emph{X...} /// \param vertex The id of the vertex - /// \returns A list containing all vertices \f$x\f$ with edges from \f$x\ldots\f$ to \f$vertex\f$ + /// \returns A list containing all vertices \emph{X} with edges from \emph{X...} to \emph{vertex} /// /// \par Complexity - /// \f$O(M)\f$ + /// \emph{O(M)} /// list incoming(size_t vertex) { list res; @@ -368,12 +366,12 @@ public: } /// - /// \brief Getter for a list of vertices \f$x\f$ that \f$vertex\f$ has an edge to and from \f$x\ldots\f$ + /// \brief Getter for a list of vertices \emph{X} that \emph{vertex} has an edge to and from \emph{X...} /// \param vertex The id of the vertex - /// \returns A list containing all vertices \f$x\f$ that have symmetric edges with \f$vertex\f$ + /// \returns A list containing all vertices \emph{X} that have symmetric edges with \emph{vertex} /// /// \par Complexity - /// \f$O(M)\f$ + /// \emph{O(M)} /// list symmetric(size_t vertex) { list res; @@ -389,16 +387,16 @@ public: } /// - /// \brief Getter for a list of vertices \f$x\f$ that \f$vertex\f$ has an edge to and from \f$x\ldots\f$ and share the same value + /// \brief Getter for a list of vertices \emph{X} that \emph{vertex} has an edge to and from \emph{X...} and share the same value /// \details /// "Joined" edges may also be referred to as "undirected." A joined, or undirected, edge may be /// turned into a directed edge by changing the weight object associated with the edge, or by /// removing one of the sub-edges. /// \param vertex The id of the vertex - /// \returns A list containing all vertices \f$x\f$ that have symmetric edges with \f$vertex\f$ + /// \returns A list containing all vertices \emph{X} that have symmetric edges with \emph{vertex} /// /// \par Complexity - /// \f$O(M)\f$ + /// \emph{O(M)} /// list undirected(size_t vertex) { list res; @@ -421,7 +419,7 @@ public: /// \returns A pointer to a map containing edges mapped from this vertex /// /// \par Complexity - /// \f$O(M)\f$ + /// \emph{O(M)} /// const auto* edges(size_t vertex) { if (is_empty() || vertex >= _edge_map.size()) { @@ -444,7 +442,7 @@ public: /// \returns The id of the new vertex /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr size_t insert(vertex_t&& vertex) { return this->_insert(fennec::forward(vertex)); @@ -456,7 +454,7 @@ public: /// \returns The id of the new vertex /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr size_t insert(const vertex_t& vertex) { return this->_insert(vertex); @@ -469,7 +467,7 @@ public: /// \returns The id of the new vertex /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// template constexpr size_t emplace(ArgsT&&...args) { @@ -481,7 +479,7 @@ public: /// \param vertex The id of the vertex to erase /// /// \par Complexity - /// \f$O(M)\f$ + /// \emph{O(M)} /// constexpr void erase(size_t vertex) { cut(vertex); @@ -489,14 +487,14 @@ public: } /// - /// \brief Form an edge from vertex \f$a\f$ to vertex \f$b\f$ + /// \brief Form an edge from vertex \emph{a} to vertex \emph{b} /// \tparam ArgsT The argument types /// \param a The first vertex id /// \param b The second vertex id /// \param args The arguments to construct the edge with /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// template constexpr void make_edge(size_t a, size_t b, ArgsT&&...args) { @@ -508,7 +506,7 @@ public: _edge_map.resize(_vertex_pool.capacity()); } - auto it = _edge_map[a][b]; + const auto it = _edge_map[a][b]; size_t conn; if (it != nullptr) { conn = *it; @@ -520,14 +518,14 @@ public: } /// - /// \brief Form an undirected edge between vertex \f$a\f$ and vertex \f$b\f$ + /// \brief Form an undirected edge between vertex \emph{a} and vertex \emph{b} /// \tparam ArgsT The argument types /// \param a The first vertex id /// \param b The second vertex id /// \param args The arguments to construct the edge with /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// template constexpr void make_edge2(size_t a, size_t b, ArgsT&&...args) { @@ -539,7 +537,7 @@ public: _edge_map.resize(_vertex_pool.capacity()); } - auto it = _edge_map[a][b]; + const auto it = _edge_map[a][b]; size_t conn; if (it != nullptr) { conn = *it; @@ -553,12 +551,12 @@ public: } /// - /// \brief Disconnect an edge from vertex \f$a\f$ to vertex \f$b\f$ + /// \brief Disconnect an edge from vertex \emph{a} to vertex \emph{b} /// \param a The first vertex id /// \param b The second vertex id /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr void cut_edge(size_t a, size_t b) { @@ -580,12 +578,12 @@ public: } /// - /// \brief Disconnect both directed edges between vertices \f$a\f$ and \f$b\f$ + /// \brief Disconnect both directed edges between vertices \emph{a} and \emph{b} /// \param a The first vertex id /// \param b The second vertex id /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr void cut_edge2(size_t a, size_t b) { const auto* ita = _edge_map[a][b]; @@ -600,11 +598,11 @@ public: } /// - /// \brief Break *all* edges connected to \f$n\f$ + /// \brief Break *all* edges connected to \emph{n} /// \param n The vertex id /// /// \par Complexity - /// \f$O(M)\f$ + /// \emph{O(M)} /// void cut(size_t n) { for (const auto it : outgoing(n)) { @@ -619,7 +617,7 @@ public: /// \brief Clear the graph, destructing all vertices and edges. /// /// \par Complexity - /// \f$O(N + M)\f$ + /// \emph{O(N + M)} /// void clear() { _vertex_pool.clear(); diff --git a/include/fennec/containers/initializer_list.h b/include/fennec/containers/initializer_list.h index c7e24cd..81e59ee 100644 --- a/include/fennec/containers/initializer_list.h +++ b/include/fennec/containers/initializer_list.h @@ -44,7 +44,7 @@ using std::initializer_list; /// /// \param inls the initializer list -/// \returns A const qualified pointer to the first element in \f$inls\f$ +/// \returns A const qualified pointer to the first element in \emph{inls} template constexpr const T* begin(initializer_list inls) noexcept { return inls.begin(); @@ -52,7 +52,7 @@ constexpr const T* begin(initializer_list inls) noexcept { /// /// \param inls the initializer list -/// \returns A const qualified pointer to one past the last element in \f$inls\f$ +/// \returns A const qualified pointer to one past the last element in \emph{inls} template constexpr const T* end(initializer_list inls) noexcept { return inls.end(); diff --git a/include/fennec/containers/list.h b/include/fennec/containers/list.h index 3f29e28..7ec3b9d 100644 --- a/include/fennec/containers/list.h +++ b/include/fennec/containers/list.h @@ -48,23 +48,22 @@ namespace fennec /// This data-structure behaves like a linked list, but does not use pointers. Instead, it is in-array. This creates the /// following properties: /// -/// | Property | Value | -/// |:-----------:|:----------:| -/// | stable | ⛔ | -/// | dynamic | ✅ | -/// | homogeneous | ✅ | -/// | distinct | ⛔ | -/// | ordered | ⛔ | -/// | space | \f$O(N)\f$ | -/// | linear | ✅ | -/// | access | \f$O(N)\f$ | -/// | find | \f$O(N)\f$ | -/// | insertion | \f$O(N)\f$ | -/// | deletion | \f$O(N)\f$ | -/// | space | \f$O(N)\f$ | +/// | Property | Value | +/// |:-----------:|:-----------:| +/// | stable | ⛔ | +/// | dynamic | ✅ | +/// | homogeneous | ✅ | +/// | distinct | ⛔ | +/// | ordered | ⛔ | +/// | linear | ✅ | +/// | space | \emph{O(N)} | +/// | access | \emph{O(N)} | +/// | find | \emph{O(N)} | +/// | insertion | \emph{O(N)} | +/// | deletion | \emph{O(N)} | /// -/// \note Access, Insertion, and Deletion are \f$O(N)\f$ using the index pattern, -/// using the iterator pattern yields \f$O(1)\f$ runtime. +/// \note Access, Insertion, and Deletion are \emph{O(N)} using the index pattern, +/// using the iterator pattern yields \emph{O(1)} runtime. /// /// \tparam TypeT value type template> @@ -106,18 +105,18 @@ public: /// \brief Default Constructor, initializes an empty list. /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr list() : _table(), _freed(), _root(npos), _last(npos), _size(0) { } /// - /// \brief Copy Constructor, copies all elements in \f$l\f$ with optimized layout + /// \brief Copy Constructor, copies all elements in \emph{l} with optimized layout /// \param l The list to copy /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// constexpr list(const list& l) : list() { @@ -132,7 +131,7 @@ public: /// \param l The list to move /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr list(list&& l) noexcept : _table(fennec::move(l._table)) @@ -146,7 +145,7 @@ public: /// \brief Destructor, destructs all elements then releases the allocation. /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// constexpr ~list() { clear(); @@ -163,10 +162,10 @@ public: /// /// \brief Copy Assignment Operator /// \param l the list to copy - /// \returns \f$this\f$ after having copied all elements of \f$l\f$ + /// \returns \emph{this} after having copied all elements of \emph{l} /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// constexpr list& operator=(const list& l) { this->clear(); @@ -179,10 +178,10 @@ public: /// /// \brief Move Assignment Operator /// \param l the list to copy - /// \returns \f$this\f$ after having taken ownership over the contents of \f$l\f$ + /// \returns \emph{this} after having taken ownership over the contents of \emph{l} /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr list& operator=(list&& l) noexcept { this->clear(); @@ -206,7 +205,7 @@ public: /// \returns The size of the list in elements. /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr size_t size() const { return _size; @@ -216,17 +215,17 @@ public: /// \returns The capacity of the list in elements. /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr size_t capacity() const { return _table.size(); } /// - /// \returns \f$true\f$ when the list is empty, \f$false\f$ otherwise. + /// \returns \emph{true} when the list is empty, \emph{false} otherwise. /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr bool is_empty() const { return _root == npos; @@ -244,10 +243,10 @@ public: /// /// \brief Array Access Operator /// \param i Index to access - /// \returns A reference to the element at \f$i\f$ + /// \returns A reference to the element at \emph{i} /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// constexpr value_t& operator[](int i) { assertd(i >= 0 && size_t(i) < _size, "Index out of Bounds"); @@ -259,10 +258,10 @@ public: /// /// \brief Const Array Access Operator /// \param i Index to access - /// \returns A const-qualified reference to the element at \f$i\f$ + /// \returns A const-qualified reference to the element at \emph{i} /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// constexpr const value_t& operator[](int i) const { assertd(i >= 0 && size_t(i) < _size, "Index out of Bounds"); @@ -276,7 +275,7 @@ public: /// \returns A reference to the first element in the list /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr value_t& front() { return *_table[_root].value; @@ -287,7 +286,7 @@ public: /// \returns A const-qualified reference to the first element in the list /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr const value_t& front() const { return *_table[_root].value; @@ -298,7 +297,7 @@ public: /// \returns A reference to the last element in the list /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr value_t& back() { return *_table[_last].value; @@ -309,7 +308,7 @@ public: /// \returns A const-qualified reference to the last element in the list /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr const value_t& back() const { return *_table[_last].value; @@ -331,7 +330,7 @@ public: /// \returns The id of the inserted node /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr iterator insert(const iterator& it, const value_t& x) { return this->_insert(it._n, x); @@ -344,7 +343,7 @@ public: /// \returns The id of the inserted node /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr iterator insert(const iterator& it, value_t&& x) { return this->_insert(it._n, fennec::forward(x)); @@ -357,7 +356,7 @@ public: /// \returns The id of the inserted node /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// constexpr iterator insert(size_t i, const value_t& x) { assert(i <= size(), "Index out of Bounds"); @@ -373,7 +372,7 @@ public: /// \returns The id of the inserted node /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// constexpr iterator insert(size_t i, value_t&& x) { assert(i <= size(), "Index out of Bounds"); @@ -390,7 +389,7 @@ public: /// \returns The id of the inserted node /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// template constexpr iterator emplace(size_t i, ArgsT&&...args) { @@ -408,7 +407,7 @@ public: /// \returns The id of the inserted node /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// template constexpr iterator emplace(const iterator& it, ArgsT&&...args) { @@ -421,7 +420,7 @@ public: /// \returns The id of the inserted node /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr iterator push_front(const value_t& x) { return this->_insert(_root, x); @@ -433,7 +432,7 @@ public: /// \returns The id of the inserted node /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr iterator push_front(value_t&& x) { return this->_insert(_root, fennec::forward(x)); @@ -446,7 +445,7 @@ public: /// \returns The id of the inserted node /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// template constexpr iterator emplace_front(ArgsT&&...args) { @@ -459,7 +458,7 @@ public: /// \returns The id of the inserted node /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr iterator push_back(const value_t& x) { return this->_insert(npos, x); @@ -471,7 +470,7 @@ public: /// \returns The id of the inserted node /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr iterator push_back(value_t&& x) { return this->_insert(npos, fennec::forward(x)); @@ -484,7 +483,7 @@ public: /// \returns The id of the inserted node /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// template constexpr iterator emplace_back(ArgsT&&...args) { @@ -496,11 +495,11 @@ public: /// \param i Index to erase /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// constexpr void erase(size_t i) { assert(i < size(), "Index out of Bounds!"); - size_t n = _walk(i); + const size_t n = _walk(i); _erase(n); } @@ -509,7 +508,7 @@ public: /// \param it Location to Erase /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr void erase(const iterator& it) { this->_erase(it._n); @@ -519,7 +518,7 @@ public: /// \brief Pop Front, erases first element /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr void pop_front() { _erase(_root); @@ -529,7 +528,7 @@ public: /// \brief Pop Back, erases first element /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr void pop_back() { _erase(_last); @@ -539,7 +538,7 @@ public: /// \brief Clears the list, destructing all elements in order /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// constexpr void clear() { size_t i = _root; @@ -564,18 +563,18 @@ public: /// \returns An iterator for the first element in the list /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr iterator begin() { return iterator(this, _root); } /// - /// \brief C++ Iterator Specification \f$begin()\f$ + /// \brief C++ Iterator Specification \emph{begin()} /// \returns A const iterator for the first element in the list /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr const_iterator begin() const { return const_iterator(this, _root); @@ -585,25 +584,25 @@ public: /// \returns An iterator for the end of the list /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr iterator end() { return iterator(this, npos); } /// - /// \brief Const C++ Iterator Specification \f$end()\f$ + /// \brief Const C++ Iterator Specification \emph{end()} /// \returns A const iterator for the end of the list /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr const_iterator end() const { return const_iterator(this, npos); } /// - /// \brief C++ Iterator Specification \f$iterator\f$ + /// \brief C++ Iterator Specification \emph{iterator} class iterator { public: /// @@ -615,7 +614,7 @@ public: /// /// \brief prefix increment operator /// \param rhs the iterator to increment - /// \returns \f$rhs\f$ after having moved to the next element in the list + /// \returns \emph{rhs} after having moved to the next element in the list constexpr friend iterator& operator++(iterator& rhs) { rhs._n = rhs._list->_next(rhs._n); return rhs; @@ -624,7 +623,7 @@ public: /// /// \brief postfix increment operator /// \param lhs the iterator to increment - /// \returns \f$lhs\f$ before having moved to the next element in the list + /// \returns \emph{lhs} before having moved to the next element in the list constexpr friend iterator operator++(iterator& lhs, int) { iterator prev = lhs; ++lhs; @@ -648,7 +647,7 @@ public: /// /// \brief iterator equality operator /// \param it the iterator to compare with - /// \returns \f$true\f$ if the iterators are identical, \f$false\f$ otherwise + /// \returns \emph{true} if the iterators are identical, \emph{false} otherwise constexpr bool operator==(const iterator& it) { return _list == it._list and _n == it._n; } @@ -656,7 +655,7 @@ public: /// /// \brief iterator inequality operator /// \param it the iterator to compare with - /// \returns \f$true\f$ if the iterators are different, \f$false\f$ otherwise + /// \returns \emph{true} if the iterators are different, \emph{false} otherwise constexpr bool operator!=(const iterator& it) { return _list != it._list or _n != it._n; } @@ -685,7 +684,7 @@ public: /// /// \brief prefix increment operator /// \param rhs the iterator to increment - /// \returns \f$rhs\f$ after having moved to the next element in the list + /// \returns \emph{rhs} after having moved to the next element in the list constexpr friend const_iterator& operator++(const_iterator& rhs) { if (rhs._list->_next(rhs._n) < rhs._list->capacity()) { return rhs; @@ -697,7 +696,7 @@ public: /// /// \brief postfix increment operator /// \param lhs the iterator to increment - /// \returns \f$lhs\f$ before having moved to the next element in the list + /// \returns \emph{lhs} before having moved to the next element in the list constexpr friend const_iterator operator++(const_iterator& lhs, int) { const_iterator prev = lhs; ++lhs; @@ -721,7 +720,7 @@ public: /// /// \brief iterator equality operator /// \param it the iterator to compare with - /// \returns \f$true\f$ if the iterators are identical, \f$false\f$ otherwise + /// \returns \emph{true} if the iterators are identical, \emph{false} otherwise constexpr bool operator==(const const_iterator& it) { return _list == it._list and _n == it._n; } @@ -729,7 +728,7 @@ public: /// /// \brief iterator inequality operator /// \param it the iterator to compare with - /// \returns \f$true\f$ if the iterators are different, \f$false\f$ otherwise + /// \returns \emph{true} if the iterators are different, \emph{false} otherwise constexpr bool operator!=(const const_iterator& it) { return _list != it._list or _n != it._n; } @@ -800,7 +799,7 @@ private: constexpr size_t _next_free() { if (not _freed.is_empty()) { - size_t n = _freed.back(); + const size_t n = _freed.back(); _freed.pop_back(); return n; } diff --git a/include/fennec/containers/map.h b/include/fennec/containers/map.h index f86160c..5a02f50 100644 --- a/include/fennec/containers/map.h +++ b/include/fennec/containers/map.h @@ -56,24 +56,23 @@ namespace fennec */ /// -/// \brief Data Structure defining a mapping of \f$key\f$ \f$KeyT\f$ to \f$value\f$ \f$ValueT\f$ +/// \brief Data Structure defining a mapping of \emph{key} \emph{KeyT} to \emph{value} \emph{ValueT} /// \details -/// | Property | Value | -/// |:-----------:|:----------:| -/// | stable | ⛔ | -/// | dynamic | ✅ | -/// | homogeneous | ✅ | -/// | distinct | ✅ | -/// | ordered | ⛔ | -/// | space | \f$O(N)\f$ | -/// | linear | ⛔ | -/// | access | \f$O(1)\f$ | -/// | find | \f$O(1)\f$ | -/// | insertion | \f$O(1)\f$ | -/// | deletion | \f$O(1)\f$ | -/// | space | \f$O(N)\f$ | +/// | Property | Value | +/// |:-----------:|:-----------:| +/// | stable | ⛔ | +/// | dynamic | ✅ | +/// | homogeneous | ✅ | +/// | distinct | ✅ | +/// | ordered | ⛔ | +/// | linear | ⛔ | +/// | space | \emph{O(N)} | +/// | access | \emph{O(1)} | +/// | find | \emph{O(1)} | +/// | insertion | \emph{O(1)} | +/// | deletion | \emph{O(1)} | /// -/// \note These runtimes are amortized, in theory the worst case is \f$O(N)\f$, but that is highly improbable. +/// \note These runtimes are amortized, in theory the worst case is \emph{O(N)}, but that is highly improbable. /// /// \tparam KeyT The Key Type /// \tparam ValueT The Value Type @@ -102,7 +101,7 @@ public: /// \brief key hash helper struct key_hash : hash_t { /// - /// \brief C++ 11 Hash Specification \f$operator()\f$ + /// \brief C++ 11 Hash Specification \emph{operator()} /// \param p the pair to hash /// \returns the hash of the key constexpr size_t operator()(const elem_t& p) const { @@ -114,10 +113,10 @@ public: /// \brief key comparison helper struct key_equals : equality { /// - /// \brief C++ 11 Compare Specification \f$operator()\f$ + /// \brief C++ 11 Compare Specification \emph{operator()} /// \param a the first pair /// \param b the second pair - /// \returns \f$true\f$ if the keys are equal, \f$false\f$ otherwise + /// \returns \emph{true} if the keys are equal, \emph{false} otherwise constexpr bool operator()(const elem_t& a, const elem_t& b) const { return equality::operator()(a.first, b.first); } @@ -156,7 +155,7 @@ public: } /// - /// \returns \f$true\f$ when there are no elements in the set, \f$false\f$ otherwise + /// \returns \emph{true} when there are no elements in the set, \emph{false} otherwise constexpr size_t is_empty() const { return _set.size(); } @@ -179,10 +178,10 @@ public: /// /// \brief Key Access Operator /// \param key Key value to access - /// \returns A pointer to the value associated with \f$key\f$, \f$nullptr\f$ if \f$key\f$ is not present. + /// \returns A pointer to the value associated with \emph{key}, \emph{nullptr} if \emph{key} is not present. /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr value_t* operator[](const KeyT& key) { auto it = _set.at(this->_find(key)); @@ -192,10 +191,10 @@ public: /// /// \brief Key Const Access Operator /// \param key Key value to access - /// \returns A const-qualified pointer to the value associated with \f$key\f$, \f$nullptr\f$ if \f$key\f$ is not present. + /// \returns A const-qualified pointer to the value associated with \emph{key}, \emph{nullptr} if \emph{key} is not present. /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr const value_t* operator[](const KeyT& key) const { auto it = _set.at(this->_find(key)); @@ -206,10 +205,10 @@ public: /// \brief Argument Key Access Operator /// \tparam ArgsT Argument Types /// \param args Arguments to construct the key with - /// \returns A pointer to the value associated with \f$key\f$, \f$nullptr\f$ if \f$key\f$ is not present. + /// \returns A pointer to the value associated with \emph{key}, \emph{nullptr} if \emph{key} is not present. /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// template constexpr value_t* operator[](ArgsT&&...args) { @@ -221,10 +220,10 @@ public: /// \brief Argument Key Const Access Operator /// \tparam ArgsT Argument Type /// \param args Argument to construct the key with - /// \returns A const-qualified pointer to the value associated with \f$key\f$, \f$nullptr\f$ if \f$key\f$ is not present. + /// \returns A const-qualified pointer to the value associated with \emph{key}, \emph{nullptr} if \emph{key} is not present. /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// template constexpr const value_t* operator[](ArgsT&&...args) const { @@ -246,7 +245,7 @@ public: /// \param pair a pair containing the key and its value /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr void insert(elem_t&& pair) { this->_insert(fennec::forward(pair)); @@ -258,7 +257,7 @@ public: /// \param args Arguments for constructing the key-value pair /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// template constexpr void emplace(const KeyT& key, ArgsT&&...args) { @@ -270,7 +269,7 @@ public: /// \param args Arguments for constructing the key-value pair /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// template constexpr void emplace(ArgsT&&...args) { @@ -282,7 +281,7 @@ public: /// \param key key to erase /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr void erase(KeyT&& key) { _set.erase(this->_find(fennec::forward(key))); @@ -293,7 +292,7 @@ public: /// \param key key to erase /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr void erase(const KeyT& key) { _set.erase(this->_find(key)); @@ -305,7 +304,7 @@ public: /// \param args Arguments to construct a key to erase /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// template constexpr void erase(ArgsT&&...args) { @@ -316,7 +315,7 @@ public: /// \brief Clears the map destructing all elements /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// void clear() { _set.clear(); @@ -332,11 +331,11 @@ public: /// @{ /// - /// \brief C++ Iterator Specification \f$begin()\f$ + /// \brief C++ Iterator Specification \emph{begin()} /// \returns an iterator at the start of the map /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr iterator begin() { return _set.begin(); @@ -344,11 +343,11 @@ public: /// - /// \brief C++ Iterator Specification \f$end()\f$ + /// \brief C++ Iterator Specification \emph{end()} /// \returns an iterator at the end of the map /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr iterator end() { return _set.end(); diff --git a/include/fennec/containers/object_pool.h b/include/fennec/containers/object_pool.h index ac5bfc6..1b26ddc 100644 --- a/include/fennec/containers/object_pool.h +++ b/include/fennec/containers/object_pool.h @@ -41,20 +41,19 @@ namespace fennec /// /// \brief Struct which holds a pool of objects associated with ids /// \details -/// | Property | Value | -/// |:-----------:|:----------:| -/// | stable | ⛔ | -/// | dynamic | ✅ | -/// | homogeneous | ✅ | -/// | distinct | ⛔ | -/// | ordered | ⛔ | -/// | space | \f$O(N)\f$ | -/// | linear | ⛔ | -/// | access | \f$O(1)\f$ | -/// | find | \f$O(N)\f$ | -/// | insertion | \f$O(1)\f$ | -/// | deletion | \f$O(1)\f$ | -/// | space | \f$O(N)\f$ | +/// | Property | Value | +/// |:-----------:|:-----------:| +/// | stable | ⛔ | +/// | dynamic | ✅ | +/// | homogeneous | ✅ | +/// | distinct | ⛔ | +/// | ordered | ⛔ | +/// | linear | ⛔ | +/// | space | \emph{O(N)} | +/// | access | \emph{O(1)} | +/// | find | \emph{O(N)} | +/// | insertion | \emph{O(1)} | +/// | deletion | \emph{O(1)} | /// /// \tparam TypeT The value type /// \tparam AllocT The allocator type @@ -88,7 +87,7 @@ public: /// \brief Default Constructor, initializes an empty object pool /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr object_pool() : _size(0) { @@ -98,7 +97,7 @@ public: /// \brief Default Destructor, destructs objects then releases the allocation. /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// constexpr ~object_pool() = default; @@ -114,7 +113,7 @@ public: /// \returns The number of active objects in the pool /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr size_t size() const { return _size; @@ -124,30 +123,30 @@ public: /// \returns The capacity of the underlying allocation /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr size_t capacity() const { return _table.capacity(); } /// - /// \returns \f$true\f$ when there are no objects in the pool, \f$false\f$ otherwise + /// \returns \emph{true} when there are no objects in the pool, \emph{false} otherwise /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr bool is_empty() const { return size() == 0; } /// - /// \brief Retrieve the next id \f$i\f$ that would be assigned to an object \f$o\f$ were it added to the object pool + /// \brief Retrieve the next id \emph{i} that would be assigned to an object \math{o} were it added to the object pool /// /// \details This can be useful if there are constant members that need to be assigned at construction. /// \returns The id of the next inserted node /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr size_t next_id() const { size_t next = _size; @@ -167,10 +166,10 @@ public: /// /// \brief Array Access Operator /// \param i id of the object - /// \returns a reference to the object with id \f$i\f$ + /// \returns a reference to the object with id \emph{i} /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr value_t& operator[](size_t i) { assert(i < capacity(), "Index out of Bounds!"); @@ -181,10 +180,10 @@ public: /// /// \brief Array Const Access Operator /// \param i id of the object - /// \returns a const-qualified reference to the object with id \f$i\f$ + /// \returns a const-qualified reference to the object with id \emph{i} /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr const value_t& operator[](size_t i) const { assert(i < capacity(), "Index out of Bounds!"); @@ -206,24 +205,24 @@ public: /// @{ /// - /// \brief Move Insertion, inserts \f$x\f$ into the pool + /// \brief Move Insertion, inserts \emph{x} into the pool /// \param x the object to move /// \returns An integer corresponding to the id of the node /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr size_t insert(value_t&& x) { return this->_insert(fennec::forward(x)); } /// - /// \brief Move Insertion, inserts a copy of \f$x\f$ into the pool + /// \brief Move Insertion, inserts a copy of \emph{x} into the pool /// \param x the object to copy /// \returns An integer corresponding to the id of the node /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr size_t insert(const value_t& x) { return this->_insert(x); @@ -231,12 +230,12 @@ public: /// - /// \brief Emplacement, constructs a new object using \f$args\ldots\f$ + /// \brief Emplacement, constructs a new object using \emph{args...} /// \param args The arguments to construct the new object with /// \returns An integer corresponding to the id of the node /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// template constexpr size_t emplace(ArgsT&&...args) { @@ -248,7 +247,7 @@ public: /// \param i The id of the object /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr void erase(size_t i) { _table[i] = nullopt; @@ -260,7 +259,7 @@ public: /// \brief Clear the object pool /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// constexpr void clear() { _table.clear(); @@ -277,18 +276,18 @@ public: /// \returns an iterator at the start of the object pool /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// iterator begin() { return iterator(this, 0); } /// - /// \brief C++ Iterator Specification \f$begin()\f$ + /// \brief C++ Iterator Specification \emph{begin()} /// \returns an iterator at the start of the object pool /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// const_iterator begin() const { return const_iterator(this, 0); @@ -298,25 +297,25 @@ public: /// \returns an iterator at the start of the end of the object pool /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// iterator end() { return iterator(this, _size); } /// - /// \brief C++ Iterator Specification \f$end()\f$ + /// \brief C++ Iterator Specification \emph{end()} /// \returns an iterator at the start of the end of the object pool /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// const_iterator end() const { return const_iterator(this, _size); } /// - /// \brief C++ Iterator Specification \f$iterator\f$ + /// \brief C++ Iterator Specification \emph{iterator} class iterator { public: /// @@ -337,18 +336,18 @@ public: /// /// \brief copy assignment /// \param it the iterator to copy - /// \returns a reference to self after having copied \f$it\f$ + /// \returns a reference to \emph{this} after having copied \emph{it} iterator& operator=(const iterator& it) = default; /// /// \brief move assignment /// \param it the iterator to move - /// \returns a reference to self after having moved \f$it\f$ + /// \returns a reference to \emph{this} after having moved \emph{it} iterator& operator=(iterator&& it) noexcept = default; /// /// \brief postfix increment operator - /// \returns \f$it\f$ before having been incremented + /// \returns \emph{it} before having been incremented friend iterator operator++(iterator& it, int) { iterator ret = it; ++it.curr; @@ -358,7 +357,7 @@ public: /// /// \brief prefix increment operator - /// \returns \f$it\f$ after having moved to the next element + /// \returns \emph{it} after having moved to the next element friend iterator& operator++(iterator& it) { ++it.curr; it._fix(); @@ -382,7 +381,7 @@ public: /// /// \brief iterator equality operator /// \param it the iterator to compare with - /// \returns \f$true\f$ if the iterators are identical, \f$false\f$ otherwise + /// \returns \emph{true} if the iterators are identical, \emph{false} otherwise bool operator==(const iterator& it) { return pool == it.pool and curr == it.curr; } @@ -390,7 +389,7 @@ public: /// /// \brief iterator inequality operator /// \param it the iterator to compare with - /// \returns \f$true\f$ if the iterators are different, \f$false\f$ otherwise + /// \returns \emph{true} if the iterators are different, \emph{false} otherwise bool operator!=(const iterator& it) { return pool != it.pool or curr != it.curr; } @@ -414,7 +413,7 @@ public: }; /// - /// \brief C++ Iterator Specification \f$const_iterator\f$ + /// \brief C++ Iterator Specification \emph{const_iterator} class const_iterator { public: /// @@ -435,18 +434,18 @@ public: /// /// \brief copy assignment /// \param it the iterator to copy - /// \returns a reference to self after having copied \f$it\f$ + /// \returns a reference to \emph{this} after having copied \emph{it} const_iterator& operator=(const const_iterator& it) = default; /// /// \brief move assignment /// \param it the iterator to move - /// \returns a reference to self after having moved \f$it\f$ + /// \returns a reference to \emph{this} after having moved \emph{it} const_iterator& operator=(const_iterator&& it) noexcept = default; /// /// \brief postfix increment operator - /// \returns \f$it\f$ before having been incremented + /// \returns \emph{it} before having been incremented friend const_iterator operator++(const_iterator& it, int) { const_iterator ret = it; ++it.curr; @@ -456,7 +455,7 @@ public: /// /// \brief prefix increment operator - /// \returns \f$it\f$ after having moved to the next element + /// \returns \emph{it} after having moved to the next element friend const_iterator& operator++(const_iterator& it) { ++it.curr; it._fix(); @@ -480,7 +479,7 @@ public: /// /// \brief iterator equality operator /// \param it the iterator to compare with - /// \returns \f$true\f$ if the iterators are identical, \f$false\f$ otherwise + /// \returns \emph{true} if the iterators are identical, \emph{false} otherwise bool operator==(const const_iterator& it) { return pool == it.pool and curr == it.curr; } @@ -488,7 +487,7 @@ public: /// /// \brief iterator inequality operator /// \param it the iterator to compare with - /// \returns \f$true\f$ if the iterators are different, \f$false\f$ otherwise + /// \returns \emph{true} if the iterators are different, \emph{false} otherwise bool operator!=(const const_iterator& it) { return pool != it.pool or curr != it.curr; } diff --git a/include/fennec/containers/optional.h b/include/fennec/containers/optional.h index cadfac6..49da3ce 100644 --- a/include/fennec/containers/optional.h +++ b/include/fennec/containers/optional.h @@ -39,34 +39,33 @@ namespace fennec { /// -/// \brief struct to represent a \f$null\f$ `fennec::optional` +/// \brief struct to represent a \emph{null} `fennec::optional` struct nullopt_t {}; /// -/// \brief value representing a \f$null\f$ `fennec::optional` +/// \brief value representing a \emph{null} `fennec::optional` constexpr nullopt_t nullopt_v = {}; /// -/// \brief alias for representing a \f$null\f$ `fennec::optional` +/// \brief alias for representing a \emph{null} `fennec::optional` #define nullopt nullopt_v /// /// \brief Structure to hold an optional value. /// \details -/// | Property | Value | -/// |:-----------:|:----------:| -/// | stable | ✅ | -/// | dynamic | ⛔ | -/// | homogeneous | ✅ | -/// | distinct | ⛔ | -/// | ordered | ⛔ | -/// | space | \f$O(N)\f$ | -/// | linear | ⛔ | -/// | access | \f$O(1)\f$ | -/// | find | ⛔ | -/// | insertion | \f$O(1)\f$ | -/// | deletion | \f$O(1)\f$ | -/// | space | \f$O(1)\f$ | +/// | Property | Value | +/// |:-----------:|:-----------:| +/// | stable | ✅ | +/// | dynamic | ⛔ | +/// | homogeneous | ✅ | +/// | distinct | ⛔ | +/// | ordered | ⛔ | +/// | linear | ⛔ | +/// | space | \emph{O(1)} | +/// | access | \emph{O(1)} | +/// | find | ⛔ | +/// | insertion | \emph{O(1)} | +/// | deletion | \emph{O(1)} | /// /// \tparam T template @@ -95,7 +94,7 @@ public: /// \brief Default Constructor /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr optional() : _root(0) @@ -106,7 +105,7 @@ public: /// \brief Default Constructor /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr optional(nullopt_t) : _root(0) @@ -118,7 +117,7 @@ public: /// \param val the value to initialize the underlying object with /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr optional(const T& val) : _val(val) @@ -130,7 +129,7 @@ public: /// \param val the value to initialize the underlying object with /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr optional(T&& val) : _val(fennec::forward(val)) @@ -142,7 +141,7 @@ public: /// \param opt the optional to copy /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr optional(const optional& opt) requires is_copy_assignable_v : optional() { @@ -157,7 +156,7 @@ public: /// \param opt the optional to move /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr optional(optional&& opt) noexcept requires is_move_assignable_v : optional() { @@ -174,7 +173,7 @@ public: /// \param args The argument values /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// template constexpr optional(ArgsT&&...args) @@ -186,7 +185,7 @@ public: /// \brief destructor /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr ~optional() { if constexpr(is_fundamental_v) { @@ -207,20 +206,20 @@ public: /// /// \brief Implicit Boolean Check - /// \returns \f$true\f$ when there is a value contained + /// \returns \emph{true} when there is a value contained /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr operator bool() const { return _set; } /// - /// \returns \f$true\f$ when there is no held value, \f$false\f$ otherwise. + /// \returns \emph{true} when there is no held value, \emph{false} otherwise. /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr bool is_empty() const { return not _set; @@ -236,10 +235,10 @@ public: /// /// \brief Null Assignment - /// \returns A reference to self + /// \returns A reference to \emph{this} /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr optional& operator=(nullopt_t) { if constexpr(not is_fundamental_v) { @@ -255,10 +254,10 @@ public: /// /// \brief Type Copy Assignment /// \param val The value to set with - /// \returns A reference to self + /// \returns A reference to \emph{this} /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr optional& operator=(const T& val) requires is_copy_constructible_v and is_copy_assignable_v { if (_set) { @@ -273,10 +272,10 @@ public: /// /// \brief Type Move Assignment /// \param val The value to set with - /// \returns A reference to self + /// \returns A reference to \emph{this} /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr optional& operator=(T&& val) requires is_move_constructible_v and is_move_assignable_v { if (_set) { @@ -291,10 +290,10 @@ public: /// /// \brief Copy Assignment /// \param opt The optional to copy - /// \returns A reference to self + /// \returns A reference to \emph{this} /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr optional& operator=(const optional& opt) requires is_copy_constructible_v and is_copy_assignable_v { if (_set != opt._set) { @@ -314,10 +313,10 @@ public: /// /// \brief Move Assignment /// \param opt The optional to move - /// \returns A reference to self + /// \returns A reference to \emph{this} /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr optional& operator=(optional&& opt) noexcept requires is_move_constructible_v and is_move_assignable_v { if (_set != opt._set) { @@ -343,20 +342,20 @@ public: /// @{ /// - /// \returns A pointer to the value, \f$nullptr\f$ if there is no value + /// \returns A pointer to the value, \emph{nullptr} if there is no value /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr pointer_t operator->() noexcept { return _set ? &_val : nullptr; } /// - /// \returns A const-qualified pointer to the value, \f$nullptr\f$ if there is no value + /// \returns A const-qualified pointer to the value, \emph{nullptr} if there is no value /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr const_pointer_t operator->() const noexcept { return _set ? &_val : nullptr; @@ -367,7 +366,7 @@ public: /// \returns A reference to the value /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr T& operator*() & noexcept { assertd(_set, "Attempted to reference the value of an unset optional"); @@ -379,7 +378,7 @@ public: /// \returns A const-qualified reference to the value /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr const T& operator*() const& noexcept { assertd(_set, "Attempted to reference the value of an unset optional"); @@ -391,7 +390,7 @@ public: /// \returns A reference to the value /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr T&& operator*() && noexcept { assertd(_set, "Attempted to reference the value of an unset optional"); @@ -403,7 +402,7 @@ public: /// \returns A const-qualified reference to the value /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr const T&& operator*() const&& noexcept { assertd(_set, "Attempted to reference the value of an unset optional"); @@ -423,7 +422,7 @@ public: /// \returns A reference to the held value /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr T& emplace(T&& val) { if (_set) { @@ -441,7 +440,7 @@ public: /// \returns A reference to the held value /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr T& emplace(const T& val) { if (_set) { @@ -459,7 +458,7 @@ public: /// \returns A reference to the held value /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// template constexpr T& emplace(ArgsT&&...args) { @@ -476,7 +475,7 @@ public: /// \brief Reset the Optional /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// void reset() { this->operator=(nullopt); diff --git a/include/fennec/containers/pair.h b/include/fennec/containers/pair.h index 7bb8162..c8494e4 100644 --- a/include/fennec/containers/pair.h +++ b/include/fennec/containers/pair.h @@ -43,20 +43,19 @@ namespace fennec /// /// \brief Struct for holding a pair of values /// \details -/// | Property | Value | -/// |:-----------:|:----------:| -/// | stable | ✅ | -/// | dynamic | ⛔ | -/// | homogeneous | ⛔ | -/// | distinct | ⛔ | -/// | ordered | ⛔ | -/// | space | \f$O(N)\f$ | -/// | linear | ✅ | -/// | access | \f$O(1)\f$ | -/// | find | ⛔ | -/// | insertion | ⛔ | -/// | deletion | ⛔ | -/// | space | \f$O(1)\f$ | +/// | Property | Value | +/// |:-----------:|:-----------:| +/// | stable | ✅ | +/// | dynamic | ⛔ | +/// | homogeneous | ⛔ | +/// | distinct | ⛔ | +/// | ordered | ⛔ | +/// | linear | ✅ | +/// | space | \emph{O(1)} | +/// | access | \emph{O(1)} | +/// | find | ⛔ | +/// | insertion | ⛔ | +/// | deletion | ⛔ | /// /// \tparam TypeT0 The type of the first value /// \tparam TypeT1 The type of the second value @@ -85,7 +84,7 @@ public: /// \brief Default Constructor, invokes default constructor for both elements /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr pair() = default; @@ -93,7 +92,7 @@ public: /// \brief Destructor, invokes destructor for both elements /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr ~pair() = default; @@ -103,7 +102,7 @@ public: /// \param y Value to copy for the first element /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr pair(const TypeT0& x, const TypeT1& y) : first(x) @@ -116,7 +115,7 @@ public: /// \param y Value to move for the first element /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr pair(TypeT0&& x, TypeT1&& y) noexcept : first(fennec::forward(x)) @@ -129,7 +128,7 @@ public: /// \param arg2 Value to initialize the first element /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// template constexpr pair(Arg1T&& arg1, Arg2T&& arg2) @@ -142,7 +141,7 @@ public: /// \param pair The pair to copy /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr pair(const pair& pair) : first(fennec::copy(pair.first)) @@ -154,7 +153,7 @@ public: /// \param pair The pair to move /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr pair(pair&& pair) noexcept : first(fennec::move(pair.first)) @@ -164,10 +163,10 @@ public: /// /// \brief Copy Assignment, copies both elements /// \param pair The pair to copy - /// \returns A reference to self + /// \returns A reference to \emph{this} /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr pair& operator=(const pair& pair) { first = fennec::copy(pair.first); @@ -178,10 +177,10 @@ public: /// /// \brief Move Assignment, moves both elements /// \param pair The pair to move - /// \returns A reference to self + /// \returns A reference to \emph{this} /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr pair& operator=(pair&& pair) { first = fennec::move(pair.first); @@ -201,10 +200,10 @@ public: /// /// \brief Equality Operator /// \param p Pair to compare with - /// \returns \f$true\f$ when both elements of each pair are equal + /// \returns \emph{true} when both elements of each pair are equal /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr bool operator==(const pair& p) const { return first == p.first and second == p.second; @@ -213,10 +212,10 @@ public: /// /// \brief Inequality Operator /// \param p Pair to compare with - /// \returns \f$true\f$ when either element of each pair are equal + /// \returns \emph{true} when either element of each pair are equal /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr bool operator!=(const pair& p) const { return first != p.first or second != p.second; @@ -225,11 +224,11 @@ public: /// /// \brief Less Than Operator /// \param p Pair to compare with - /// \returns lexical comparison of both elements, i.e. returns \f$true\f$ when the first element is less, or they are + /// \returns lexical comparison of both elements, i.e. returns \emph{true} when the first element is less, or they are /// equal and the second element is less /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr bool operator<(const pair& p) const { return first < p.first or (first == p.first and second < p.second); @@ -238,11 +237,11 @@ public: /// /// \brief Less Equal Operator /// \param p Pair to compare with - /// \returns lexical comparison of both elements, i.e. returns \f$true\f$ when the first element is less, or they are + /// \returns lexical comparison of both elements, i.e. returns \emph{true} when the first element is less, or they are /// equal and the second element is less or equal /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr bool operator<=(const pair& p) const { return first < p.first or (first == p.first and second <= p.second); @@ -251,11 +250,11 @@ public: /// /// \brief Greater Than Operator /// \param p Pair to compare with - /// \returns lexical comparison of both elements, i.e. returns \f$true\f$ when the first element is greater, or they are + /// \returns lexical comparison of both elements, i.e. returns \emph{true} when the first element is greater, or they are /// equal and the second element is greater /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr bool operator>(const pair& p) const { return first > p.first or (first == p.first and second > p.second); @@ -264,11 +263,11 @@ public: /// /// \brief Greater Equal Operator /// \param p Pair to compare with - /// \returns lexical comparison of both elements, i.e. returns \f$true\f$ when the first element is greater, or they are + /// \returns lexical comparison of both elements, i.e. returns \emph{true} when the first element is greater, or they are /// equal and the second element is greater or equal /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr bool operator>=(const pair& p) const { return first > p.first or (first == p.first and second >= p.second); @@ -284,9 +283,9 @@ public: template struct hash> : hash, hash { /// - /// \brief C++ 11 Hash Specification \f$operator()\f$ + /// \brief C++ 11 Hash Specification \emph{operator()} /// \param p The pair to hash - /// \returns a pairing of the hashes of both elements of \f$p\f$ using `fennec::pair_hash` + /// \returns a pairing of the hashes of both elements of \emph{p} using `fennec::pair_hash` constexpr size_t operator()(const pair& p) const { return fennec::pair_hash( // pair the hashes of both elements hash::operator()(p.first), diff --git a/include/fennec/containers/priority_queue.h b/include/fennec/containers/priority_queue.h index 4980ff2..f391e1f 100644 --- a/include/fennec/containers/priority_queue.h +++ b/include/fennec/containers/priority_queue.h @@ -56,20 +56,20 @@ namespace fennec /// /// \brief a priority queue data structure implemented using a binary heap /// \details -/// | Property | Value | -/// |:-----------:|:----------:| -/// | stable | ⛔ | -/// | dynamic | ✅ | -/// | homogeneous | ✅ | -/// | distinct | ⛔ | -/// | ordered | ✅ | -/// | space | \f$O(N)\f$ | -/// | linear | ✅ | -/// | access | \f$O(1)\f$ | -/// | find | ⛔ | -/// | insertion | \f$O(1)\f$ | -/// | deletion | \f$O(1)\f$ | -/// | space | \f$O(N)\f$ | +/// | Property | Value | +/// |:-----------:|:-----------:| +/// | stable | ⛔ | +/// | dynamic | ✅ | +/// | homogeneous | ✅ | +/// | distinct | ⛔ | +/// | ordered | ✅ | +/// | space | \emph{O(N)} | +/// | linear | ✅ | +/// | access | \emph{O(1)} | +/// | find | ⛔ | +/// | insertion | \emph{O(1)} | +/// | deletion | \emph{O(1)} | +/// | space | \emph{O(N)} | /// /// \tparam ValueT The value type /// \tparam CompareT The compare type, defaults to `fennec::less` @@ -115,7 +115,7 @@ public: /// \details initializes an empty queue /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr priority_queue() : _size(0) { @@ -125,7 +125,7 @@ public: /// \brief destructor /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// constexpr ~priority_queue() { while (_size > 0) { @@ -142,7 +142,7 @@ public: /// \returns the size of the queue /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr size_t size() const { return _size; @@ -152,17 +152,17 @@ public: /// \returns the capacity of the underlying allocation /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr size_t capacity() const { return _table.capacity(); } /// - /// \returns \f$true\f$ if the queue holds no elements + /// \returns \emph{true} if the queue holds no elements /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr bool is_empty() const { return size() == 0; @@ -176,7 +176,7 @@ public: /// \returns the value at the front of the queue /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr const value_t& front() const { return _table[0]; @@ -191,7 +191,7 @@ public: /// \param key the key to insert /// /// \par Complexity - /// \f$O(\log N)\f$ + /// \emph{O(\log N)} /// constexpr void push(const value_t& key) { this->_insert(key); @@ -201,7 +201,7 @@ public: /// \param key the key to insert /// /// \par Complexity - /// \f$O(\log N)\f$ + /// \emph{O(\log N)} /// constexpr void push(value_t&& key) { this->_insert(fennec::forward(key)); @@ -213,7 +213,7 @@ public: /// \param args the argument values /// /// \par Complexity - /// \f$O(\log N)\f$ + /// \emph{O(\log N)} /// template constexpr void emplace(ArgsT&&...args) { @@ -224,7 +224,7 @@ public: /// \brief pop the element at the front of the queue /// /// \par Complexity - /// \f$O(\log N)\f$ + /// \emph{O(\log N)} /// constexpr void pop() { fennec::swap(_table[0], _table[--_size]); diff --git a/include/fennec/containers/rdtree.h b/include/fennec/containers/rdtree.h index 249f5a4..5698067 100644 --- a/include/fennec/containers/rdtree.h +++ b/include/fennec/containers/rdtree.h @@ -32,7 +32,7 @@ #define FENNEC_CONTAINERS_RDTREE_H #include -#include +#include #include #include @@ -44,20 +44,19 @@ namespace fennec /// /// \brief Rooted-Directed Tree /// \details -/// | Property | Value | -/// |:-----------:|:----------:| -/// | stable | ⛔ | -/// | dynamic | ✅ | -/// | homogeneous | ✅ | -/// | distinct | ⛔ | -/// | ordered | ⛔ | -/// | space | \f$O(N)\f$ | -/// | linear | ⛔ | -/// | access | \f$O(1)\f$ | -/// | find | \f$O(N)\f$ | -/// | insertion | \f$O(1)\f$ | -/// | deletion | \f$O(1)\f$ | -/// | space | \f$O(N)\f$ | +/// | Property | Value | +/// |:-----------:|:-----------:| +/// | stable | ⛔ | +/// | dynamic | ✅ | +/// | homogeneous | ✅ | +/// | distinct | ⛔ | +/// | ordered | ⛔ | +/// | linear | ⛔ | +/// | space | \emph{O(N)} | +/// | access | \emph{O(1)} | +/// | find | \emph{O(N)} | +/// | insertion | \emph{O(1)} | +/// | deletion | \emph{O(1)} | /// /// \tparam TypeT Data type /// \tparam AllocT Allocator Type @@ -133,7 +132,7 @@ public: /// \param args The arguments to construct the root with /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// template explicit constexpr rdtree(ArgsT&&...args) @@ -143,23 +142,62 @@ public: } /// - /// \brief Copy Constructor, copies the contents of \f$tree\f$ + /// \brief Copy Constructor, copies the contents of \emph{tree} /// \param tree the rdtree to copy /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// - constexpr rdtree(const rdtree& tree) - : _table(tree._table), _freed(tree._freed), _size(tree._size) { - // TODO: properly invoke copy constructor for all elements + constexpr rdtree(const rdtree& tree) { + _table.reallocate(tree.size()); + + // Stack used for depth-first traversal + deque visit; + deque stack; + + // Push the root to the visit queue if the tree isn't empty + if (not tree.is_empty()) { + stack.push_back(npos); + visit.push_back(root); + } + + // Iterate + while (not visit.is_empty()) { + + // Pop the next node + const size_t node = visit.front(); + visit.pop_front(); + + // Get the next node and the child + const size_t next = tree.next(node); + const size_t child = tree.child(node); + + // Fix stack + while (tree.depth(node) < stack.size()) { + stack.pop_back(); + } + + // Add this node + stack.push_back(insert(stack.back(), npos, tree[node])); + + // Push the next node + if (next != npos) { + visit.push_front(next); + } + + // Push the child + if (child != npos) { + visit.push_front(child); + } + } } /// - /// \brief Move Constructor, takes ownership over the contents of \f$tree\f$ + /// \brief Move Constructor, takes ownership over the contents of \emph{tree} /// \param tree the rdtree to move /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr rdtree(rdtree&& tree) noexcept : _table(fennec::move(tree._table)), _freed(fennec::move(tree._freed)), _size(tree._size) { @@ -176,10 +214,10 @@ public: /// /// \brief Copy Assignment Operator /// \param rhs the rdtree to copy - /// \returns \f$this\f$ after copying the contents of \f$rhs\f$ + /// \returns \emph{this} after copying the contents of \emph{rhs} /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// constexpr rdtree& operator=(const rdtree& rhs) { // TODO: properly invoke copy constructor for all elements @@ -195,10 +233,10 @@ public: /// /// \brief Move Assignment Operator /// \param rhs the rdtree to move - /// \returns \f$this\f$ after taking ownership over the contents of \f$rhs\f$ + /// \returns \emph{this} after taking ownership over the contents of \emph{rhs} /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr rdtree& operator=(rdtree&& rhs) noexcept { for (value_t* it : _table) { @@ -221,7 +259,7 @@ public: /// \returns The number of nodes in the tree /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr size_t size() const { return _size; @@ -231,17 +269,17 @@ public: /// \returns The capacity of the underlying allocation /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr size_t capacity() const { return _table.capacity(); } /// - /// \returns \f$true\f$ when there are no nodes in the tree, \f$false\f$ otherwise + /// \returns \emph{true} when there are no nodes in the tree, \emph{false} otherwise /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr bool is_empty() const { return _size == 0; @@ -260,7 +298,7 @@ public: /// \returns The id of the parent node /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr size_t parent(size_t i) const { if (i >= _table.capacity()) return npos; @@ -273,11 +311,11 @@ public: /// \returns The id of the child node /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr size_t child(size_t i, size_t n = 0) const { if (i >= _table.capacity() && n != npos) return npos; - size_t c = i == npos ? npos : _table[i].child; + const size_t c = i == npos ? npos : _table[i].child; if (n != 0) return next(c, n == npos ? npos : n - 1); return c; @@ -289,7 +327,7 @@ public: /// \returns The id of the next node /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr size_t next(size_t i, size_t n = 0) const { if (i >= _table.capacity() && n != npos) return npos; @@ -297,7 +335,7 @@ public: return npos; } - size_t org = i; + const size_t org = i; size_t nxt = _table[i].next; while (nxt != npos) { i = nxt; @@ -318,7 +356,7 @@ public: /// \returns The id of the previous node /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr size_t prev(size_t i, size_t n = 0) const { if (i >= _table.capacity()) return npos; @@ -326,7 +364,7 @@ public: return npos; } - size_t org = i; + const size_t org = i; size_t prv = _table[i].prev; while (prv != npos) { i = prv; @@ -343,10 +381,10 @@ public: /// /// \param i the node to start at - /// \returns the left-most child of node \f$i\f$ + /// \returns the left-most child of node \emph{i} /// /// \par Complexity - /// \f$O(\log N)\f$ + /// \emph{O(\log N)} /// constexpr size_t left_most(size_t i) const { if (i >= _table.capacity()) return npos; @@ -355,7 +393,7 @@ public: return i; } while (true) { - size_t p = n; + const size_t p = n; if ((n = child(n)) == npos) { return p; } @@ -364,10 +402,10 @@ public: /// /// \param i the node to start at - /// \returns the right-most child of node \f$i\f$ + /// \returns the right-most child of node \emph{i} /// /// \par Complexity - /// \f$O(\log N)\f$ + /// \emph{O(\log N)} /// constexpr size_t right_most(size_t i) const { if (i >= _table.capacity()) return npos; @@ -391,7 +429,7 @@ public: /// \returns The depth of the node /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr size_t depth(size_t i) const { if (i >= _table.capacity()) return npos; @@ -403,7 +441,7 @@ public: /// \returns The number of children the node has /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr size_t num_children(size_t i) const { if (i >= _table.capacity()) return 0; @@ -411,10 +449,10 @@ public: } /// - /// \returns The next node id were \f$insert\f$ or \f$emplace\f$ to be called + /// \returns The next node id were \emph{insert} or \emph{emplace} to be called /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr size_t next_id() const { size_t i = _size; @@ -429,7 +467,7 @@ public: /// \returns A reference to the value of the node wrapped in an optional /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr value_t& operator[](size_t i) { return _table[i].value; @@ -440,7 +478,7 @@ public: /// \returns A const-qualified reference to the value of the node wrapped in an optional /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr const value_t& operator[](size_t i) const { return _table[i].value; @@ -455,28 +493,28 @@ public: /// @{ /// - /// \brief Insertion, creates a node in the tree with parent \f$parent\f$ - /// \param parent the parent node, if \f$npos\f$ sets the value of the root node + /// \brief Insertion, creates a node in the tree with parent \emph{parent} + /// \param parent the parent node, if \emph{npos} sets the value of the root node /// \param next the next node, as an index relative to the parent, i.e. parent[0] == parent.child, parent[1] == parent.child.next /// \param val the value to insert /// \returns the index of the created node /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr size_t insert(size_t parent, size_t next, const value_t& val) { return this->_insert(parent, next, val); } /// - /// \brief Insertion, creates a node in the tree with parent \f$parent\f$ - /// \param parent the parent node, if \f$npos\f$ sets the value of the root node + /// \brief Insertion, creates a node in the tree with parent \emph{parent} + /// \param parent the parent node, if \emph{npos} sets the value of the root node /// \param next the next node, as an index relative to the parent /// \param val the value to insert /// \returns the index of the created node /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr size_t insert(size_t parent, size_t next, value_t&& val) { return this->_insert(parent, next, fennec::forward(val)); @@ -484,13 +522,13 @@ public: /// /// \brief tree insertion, copies the contents of tree into self with the root at the specified node location - /// \param parent the parent node, if \f$npos\f$ sets the value of the root node + /// \param parent the parent node, if \emph{npos} sets the value of the root node /// \param next the next node, as an index relative to the parent /// \param tree the tree to insert /// \returns the index of the inserted root /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr size_t insert(size_t parent, size_t next, const rdtree& tree) { list> visit; @@ -516,14 +554,14 @@ public: } /// - /// \brief Insertion, creates a node in the tree with parent \f$parent\f$ - /// \param parent the parent node, if \f$npos\f$ sets the value of the root node + /// \brief Insertion, creates a node in the tree with parent \emph{parent} + /// \param parent the parent node, if \emph{npos} sets the value of the root node /// \param next the next node, as an index relative to the parent, i.e. parent[0] == parent.child, parent[1] == parent.child.next /// \param args the args to construct the value to insert /// \returns the index of the created node /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// template constexpr size_t emplace(size_t parent, size_t next, ArgsT&&...args) { @@ -536,7 +574,7 @@ public: /// \param i1 The id of the second node /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr void swap(size_t i0, size_t i1) { assertf(i0 != root and i1 != root, "Cannot Swap With Root"); @@ -575,16 +613,16 @@ public: /// \brief Traverse the tree using a specified order and visiting functor /// /// \details - /// The visitor should accept a reference to a value of type \f$TypeT\f$ and a \f$size_t\f$ which contains the node's id. + /// The visitor should accept a reference to a value of type \emph{TypeT} and a \emph{size_t} which contains the node's id. /// The visitor should return one of the following values in the `fennec::traversal_control_` enum /// /// \tparam OrderT The order with which to traverse the tree. - /// \tparam VisitorT The visitor, should fulfill the signature \f$uint8_t visit(TypeT&, size_t)\f$ + /// \tparam VisitorT The visitor, should fulfill the signature \emph{uint8_t visit(TypeT&, size_t)} /// \param visit The visiting object /// \param i The node to start at /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// template constexpr void traverse(VisitorT&& visit, size_t i = root) { @@ -606,16 +644,16 @@ public: /// \brief Traverse the tree using a specified order and visiting functor /// /// \details - /// The visitor should accept a reference to a value of type \f$TypeT\f$ and a \f$size_t\f$ which contains the node's id. + /// The visitor should accept a reference to a value of type \emph{TypeT} and a \emph{size_t} which contains the node's id. /// The visitor should return one of the following values in the `fennec::traversal_control_` enum /// /// \tparam OrderT The order with which to traverse the tree. - /// \tparam VisitorT The visitor, should fulfill the signature \f$uint8_t visit(TypeT&, size_t)\f$ + /// \tparam VisitorT The visitor, should fulfill the signature \emph{uint8_t visit(TypeT&, size_t)} /// \param visit The visiting object /// \param i The node to start at /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// template constexpr void traverse(VisitorT&& visit, size_t i = root) const { @@ -657,8 +695,8 @@ public: return npos; } - size_t nxt = tree.next(node); - size_t chd = tree.next(node); + const size_t nxt = tree.next(node); + const size_t chd = tree.next(node); if (nxt != npos && node != head) { visit.push_front(nxt); @@ -680,7 +718,7 @@ public: private: list visit; - size_t head; + size_t head = npos; }; /// @@ -707,8 +745,8 @@ public: return npos; } - size_t nxt = tree.next(node); - size_t chd = tree.child(node); + const size_t nxt = tree.next(node); + const size_t chd = tree.child(node); if (nxt != npos && node != head) { visit.push_front(nxt); @@ -730,7 +768,7 @@ public: private: list visit; - size_t head; + size_t head = npos; }; /// @@ -757,8 +795,8 @@ public: return npos; } - size_t prnt = tree.parent(node); - size_t next = tree.next(node); + const size_t prnt = tree.parent(node); + const size_t next = tree.next(node); if (node != head) { if (tree.child(prnt) == node) { visit.push_back(prnt); @@ -782,7 +820,7 @@ public: private: list visit; - size_t head; + size_t head = npos; }; /// @@ -809,8 +847,8 @@ public: return npos; } - size_t prnt = tree.parent(node); - size_t next = tree.next(node); + const size_t prnt = tree.parent(node); + const size_t next = tree.next(node); if (node != head) { if (next != npos) { @@ -832,7 +870,7 @@ public: private: list visit; - size_t head; + size_t head = npos; }; /// @} diff --git a/include/fennec/containers/sequence.h b/include/fennec/containers/sequence.h index 6ae5729..29e9982 100644 --- a/include/fennec/containers/sequence.h +++ b/include/fennec/containers/sequence.h @@ -56,20 +56,19 @@ namespace fennec /// \details /// This data-structure behaves like an ordered-set, but does not use pointers, instead storing the table in-array /// -/// | Property | Value | -/// |:-----------:|:---------------:| -/// | stable | ✅ | -/// | dynamic | ✅ | -/// | homogeneous | ✅ | -/// | distinct | ✅ | -/// | ordered | ✅ | -/// | space | \f$O(N)\f$ | -/// | linear | ✅ | -/// | access | \f$O(\log N)\f$ | -/// | find | \f$O(\log N)\f$ | -/// | insertion | \f$O(\log N)\f$ | -/// | deletion | \f$O(\log N)\f$ | -/// | space | \f$O(N)\f$ | +/// | Property | Value | +/// |:-----------:|:----------------:| +/// | stable | ✅ | +/// | dynamic | ✅ | +/// | homogeneous | ✅ | +/// | distinct | ✅ | +/// | ordered | ✅ | +/// | linear | ✅ | +/// | space | \emph{O(N)} | +/// | access | \emph{O(\log N)} | +/// | find | \emph{O(\log N)} | +/// | insertion | \emph{O(\log N)} | +/// | deletion | \emph{O(\log N)} | /// /// \tparam TypeT The type to contain /// \tparam CompareT Function for comparing two values @@ -141,27 +140,27 @@ private: // Member Access Helpers - constexpr value_t& _key(node n) { + static constexpr value_t& _key(node n) { return n->key; } - constexpr bool& _color(node n) { + static constexpr bool& _color(node n) { return n->color; } - constexpr node& _parent(node n) { + static constexpr node& _parent(node n) { return n->parent; } - constexpr node& _child(node n, bool dir) { + static constexpr node& _child(node n, bool dir) { return n->child[dir]; } - constexpr node& _left(node n) { + static constexpr node& _left(node n) { return n->child[dir_left]; } - constexpr node& _right(node n) { + static constexpr node& _right(node n) { return n->child[dir_right]; } @@ -174,7 +173,7 @@ private: } constexpr bool color(node n) { - return n ? n->color : (bool)black; + return n ? n->color : bool(black); } constexpr node parent(node n) { @@ -224,7 +223,7 @@ public: /// \brief Default Constructor, initializes an empty sequence /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr sequence() : _root(nullptr), _size(0) { @@ -234,7 +233,7 @@ public: /// \brief Move Constructor, takes ownership of a sequence /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr sequence(sequence&&) noexcept = default; @@ -247,7 +246,7 @@ public: /// \brief Default Destructor, destructs elements *in-order* /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// constexpr ~sequence() { this->clear(); @@ -261,12 +260,12 @@ public: /// @{ /// - /// \brief Value Find Function, finds the iterator position for \f$val\f$, otherwise returns \f$end()\f$ + /// \brief Value Find Function, finds the iterator position for \emph{val}, otherwise returns \emph{end()} /// \param val The value to find /// \returns An iterator at the value /// /// \par Complexity - /// \f$O(\log N)\f$ + /// \emph{O(\log N)} /// constexpr iterator find(const value_t& val) { node node = _root; @@ -285,7 +284,7 @@ public: /// /// \brief Value Contains Function, checks if the sequence contains a value /// \param val The value to find - /// \returns \f$true\f$ if \f$val\f$ is in the sequence, \f$false\f$ otherwise + /// \returns \emph{true} if \emph{val} is in the sequence, \emph{false} otherwise bool contains(const value_t& val) { return find(val) != end(); } @@ -302,17 +301,17 @@ public: /// \returns The number of elements in the sequence /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr size_t size() const { return _size; } /// - /// \returns \f$true\f$ when there are no elements in the sequence, \f$false\f$ otherwise. + /// \returns \emph{true} when there are no elements in the sequence, \emph{false} otherwise. /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr bool is_empty() const { return _size == 0; @@ -326,11 +325,11 @@ public: /// @{ /// - /// \brief Move Insertion, moves \f$val\f$ into the sequence + /// \brief Move Insertion, moves \emph{val} into the sequence /// \param val The value to insert /// /// \par Complexity - /// \f$O(\log N)\f$ + /// \emph{O(\log N)} /// constexpr void insert(value_t&& val) { node i = _insert_bst(fennec::forward(val)); @@ -338,11 +337,11 @@ public: } /// - /// \brief Copy Insertion, inserts a copy of \f$val\f$ into the sequence + /// \brief Copy Insertion, inserts a copy of \emph{val} into the sequence /// \param val The value to insert /// /// \par Complexity - /// \f$O(\log N)\f$ + /// \emph{O(\log N)} /// constexpr void insert(const value_t& val) { node i = _insert_bst(val); @@ -355,7 +354,7 @@ public: /// \param args The arguments to construct with /// /// \par Complexity - /// \f$O(\log N)\f$ + /// \emph{O(\log N)} /// template constexpr void emplace(ArgsT&&...args) { @@ -368,7 +367,7 @@ public: /// \param val the value to erase /// /// \par Complexity - /// \f$O(\log N)\f$ + /// \emph{O(\log N)} /// constexpr void erase(const value_t& val) { _erase(find(val)._node); @@ -378,7 +377,7 @@ public: /// \brief Destructs all elements, *in-order*, contained in the sequence /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// constexpr void clear() { list visit; @@ -400,18 +399,18 @@ public: /// \returns An iterator at the smallest element in the sequence /// /// \par Complexity - /// \f$O(\log N)\f$ + /// \emph{O(\log N)} /// constexpr iterator begin() { return sequence::iterator(this, _root); } /// - /// \brief C++ Iterator Specification \f$begin()\f$ + /// \brief C++ Iterator Specification \emph{begin()} /// \returns An iterator at the smallest element in the sequence /// /// \par Complexity - /// \f$O(\log N)\f$ + /// \emph{O(\log N)} /// constexpr const_iterator begin() const { return sequence::const_iterator(this, _root); @@ -421,32 +420,32 @@ public: /// \returns An iterator after the largest element in the sequence /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr iterator end() { return sequence::iterator(this, _root, nullptr); } /// - /// \brief Const C++ Iterator Specification \f$end()\f$ + /// \brief Const C++ Iterator Specification \emph{end()} /// \returns An iterator after the largest element in the sequence /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr const_iterator end() const { return sequence::const_iterator(this, _root, nullptr); } /// - /// \brief C++ Iterator Specification \f$iterator\f$ + /// \brief C++ Iterator Specification \emph{iterator} class iterator { public: /// /// \brief prefix increment operator /// \param it the iterator to increment - /// \returns \f$it\f$ after having moved to the next element in the list + /// \returns \emph{it} after having moved to the next element in the list friend iterator& operator++(iterator& it) { if (it._node == nullptr) { return it; @@ -477,7 +476,7 @@ public: /// /// \brief postfix increment operator /// \param it the iterator to increment - /// \returns \f$it\f$ before having moved to the next element in the list + /// \returns \emph{it} before having moved to the next element in the list friend iterator operator++(iterator& it, int) { iterator prev = it; ++it; @@ -502,7 +501,7 @@ public: /// \brief iterator equality operator /// \param lhs the iterator /// \param rhs the iterator to compare with - /// \returns \f$true\f$ if the iterators are identical, \f$false\f$ otherwise + /// \returns \emph{true} if the iterators are identical, \emph{false} otherwise constexpr friend bool operator==(const iterator& lhs, const iterator& rhs) { return lhs._seq == rhs._seq and lhs._node == rhs._node; } @@ -511,7 +510,7 @@ public: /// \brief iterator inequality operator /// \param lhs the iterator /// \param rhs the iterator to compare with - /// \returns \f$true\f$ if the iterators are different, \f$false\f$ otherwise + /// \returns \emph{true} if the iterators are different, \emph{false} otherwise constexpr friend bool operator!=(const iterator& lhs, const iterator& rhs) { return lhs._seq != rhs._seq or lhs._node != rhs._node; } @@ -538,14 +537,14 @@ public: }; /// - /// \brief C++ Iterator Specification \f$iterator\f$ + /// \brief C++ Iterator Specification \emph{iterator} class const_iterator { public: /// /// \brief prefix increment operator /// \param it the iterator to increment - /// \returns \f$it\f$ after having moved to the next element in the list + /// \returns \emph{it} after having moved to the next element in the list friend const_iterator& operator++(const_iterator& it) { if (it._node == nullptr) { return it; @@ -576,7 +575,7 @@ public: /// /// \brief postfix increment operator /// \param it the iterator to increment - /// \returns \f$it\f$ before having moved to the next element in the list + /// \returns \emph{it} before having moved to the next element in the list friend const_iterator operator++(const_iterator& it, int) { const_iterator prev = it; ++it; @@ -601,7 +600,7 @@ public: /// \brief iterator equality operator /// \param lhs the iterator /// \param rhs the iterator to compare with - /// \returns \f$true\f$ if the iterators are identical, \f$false\f$ otherwise + /// \returns \emph{true} if the iterators are identical, \emph{false} otherwise constexpr friend bool operator==(const const_iterator& lhs, const const_iterator& rhs) { return lhs._seq == rhs._seq and lhs._node == rhs._node; } @@ -610,7 +609,7 @@ public: /// \brief iterator inequality operator /// \param lhs the iterator /// \param rhs the iterator to compare with - /// \returns \f$true\f$ if the iterators are different, \f$false\f$ otherwise + /// \returns \emph{true} if the iterators are different, \emph{false} otherwise constexpr friend bool operator!=(const const_iterator& lhs, const const_iterator& rhs) { return lhs._seq != rhs._seq or lhs._node != rhs._node; } diff --git a/include/fennec/containers/set.h b/include/fennec/containers/set.h index 8c1dc1c..cb53608 100644 --- a/include/fennec/containers/set.h +++ b/include/fennec/containers/set.h @@ -49,20 +49,19 @@ namespace fennec /// \details /// This data-structure behaves like a set, but does not use pointers, instead storing the table in-array /// -/// | Property | Value | -/// |:-----------:|:----------:| -/// | stable | ⛔ | -/// | dynamic | ✅ | -/// | homogeneous | ✅ | -/// | distinct | ✅ | -/// | ordered | ⛔ | -/// | space | \f$O(N)\f$ | -/// | linear | ✅ | -/// | access | \f$O(1)\f$ | -/// | find | \f$O(1)\f$ | -/// | insertion | \f$O(1)\f$ | -/// | deletion | \f$O(1)\f$ | -/// | space | \f$O(N)\f$ | +/// | Property | Value | +/// |:-----------:|:-----------:| +/// | stable | ⛔ | +/// | dynamic | ✅ | +/// | homogeneous | ✅ | +/// | distinct | ✅ | +/// | ordered | ⛔ | +/// | linear | ✅ | +/// | space | \emph{O(N)} | +/// | access | \emph{O(1)} | +/// | find | \emph{O(1)} | +/// | insertion | \emph{O(1)} | +/// | deletion | \emph{O(1)} | /// /// \tparam TypeT The type to contain template, class Equals = equality, class Alloc = allocator> @@ -112,7 +111,7 @@ public: /// \brief Default Constructor, initializes empty set /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr set() : _table() @@ -127,7 +126,7 @@ public: /// \param hash the hash object /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr set(const hash_t& hash) : _table() @@ -142,7 +141,7 @@ public: /// \param alloc the allocator object /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// constexpr set(const alloc_t& alloc) : _table(alloc) @@ -158,7 +157,7 @@ public: /// \param alloc the allocator object /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr set(const hash_t& hash, const alloc_t& alloc) : _table(alloc) @@ -173,7 +172,7 @@ public: /// \param set Set to copy /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr set(const set& set) : _table(set._table) @@ -188,7 +187,7 @@ public: /// \param set Set to move /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr set(set&& set) noexcept : _table(fennec::move(set._table)) @@ -202,7 +201,7 @@ public: /// \brief Destructor, destructs all elements and releases the allocation /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// constexpr ~set() { for (size_t i = 0; i < capacity(); ++i) { @@ -222,17 +221,17 @@ public: /// \returns Size of the set in elements /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr size_t size() const { return _size; } /// - /// \returns \f$true\f$ when the set is empty, \f$false\f$ otherwise + /// \returns \emph{true} when the set is empty, \emph{false} otherwise /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr bool is_empty() const { return _size == 0; @@ -242,7 +241,7 @@ public: /// \returns Capacity of the set in elements /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr size_t capacity() const { return _table.size(); @@ -262,7 +261,7 @@ public: /// \returns An iterator at the location of the value /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr iterator find(const elem_t& val) const { if (capacity() == 0) { @@ -311,10 +310,10 @@ public: /// /// \brief Check if a set contains a value /// \param val Value to check - /// \returns \f$true\f$ if \f$val\f$ can be found, \f$false\f$ otherwise + /// \returns \emph{true} if \emph{val} can be found, \emph{false} otherwise /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr bool contains(const elem_t& val) const { return this->find(val) != end(); @@ -323,11 +322,11 @@ public: /// /// \brief Iterator Access /// \param it Location to access - /// \returns A pointer to the element, \f$nullptr\f$ if not found. + /// \returns A pointer to the element, \emph{nullptr} if not found. /// The value should not be changed in a manner that will change the hash of the element. /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr elem_t* at(const iterator& it) { if (it == end()) { @@ -342,10 +341,10 @@ public: /// /// \brief Iterator Const Access /// \param it Location to access - /// \returns A const-qualified pointer to the element, \f$nullptr\f$ if not found. + /// \returns A const-qualified pointer to the element, \emph{nullptr} if not found. /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr const elem_t* at(const iterator& it) const { if (not _table[it._i].value) return nullptr; @@ -365,7 +364,7 @@ public: /// \returns An iterator at the held value /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr iterator insert(elem_t&& val) { return this->_insert(fennec::forward(val)); @@ -377,7 +376,7 @@ public: /// \returns An iterator at the held value /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr iterator insert(const elem_t& val) { return this->_insert(val); @@ -390,7 +389,7 @@ public: /// \returns An iterator at the held value /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// template constexpr iterator emplace(ArgsT&&...args) { @@ -402,7 +401,7 @@ public: /// \param it Location to erase /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr void erase(iterator it) { size_t i = it._i; @@ -431,7 +430,7 @@ public: /// \param val Value to erase /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr void erase(const elem_t& val) { this->erase(this->find(val)); @@ -441,7 +440,7 @@ public: /// \brief Clear all elements from the set, destructing them /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// constexpr void clear() { _table.clear(); @@ -456,11 +455,11 @@ public: /// @{ /// - /// \brief C++ Iterator Specification \f$begin()\f$ + /// \brief C++ Iterator Specification \emph{begin()} /// \returns An iterator for all elements of the set in no particular order /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr iterator begin() const { iterator it(this, 0); @@ -471,11 +470,11 @@ public: } /// - /// \brief C++ Iterator Specification \f$end()\f$ + /// \brief C++ Iterator Specification \emph{end()} /// \returns An iterator representing the end of the set /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// constexpr iterator end() const { return iterator(this, npos); @@ -484,10 +483,10 @@ public: /// @} /// - /// \brief C++ Iterator Specification \f$iterator\f$ + /// \brief C++ Iterator Specification \emph{iterator} /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// class iterator { public: @@ -500,7 +499,7 @@ public: /// /// \brief prefix increment operator /// \param it the iterator to increment - /// \returns \f$it\f$ after having moved to the next element in the list + /// \returns \emph{it} after having moved to the next element in the list constexpr friend iterator& operator++(iterator& it) { while (++it._i < it._set->capacity()) { if (it._set->_table[it._i].value) { @@ -514,7 +513,7 @@ public: /// /// \brief postfix increment operator /// \param it the iterator to increment - /// \returns \f$it\f$ before having moved to the next element in the list + /// \returns \emph{it} before having moved to the next element in the list constexpr friend iterator operator++(iterator& it, int) { iterator prev = it; ++it; @@ -539,7 +538,7 @@ public: /// /// \brief iterator equality operator /// \param it the iterator to compare with - /// \returns \f$true\f$ if the iterators are identical, \f$false\f$ otherwise + /// \returns \emph{true} if the iterators are identical, \emph{false} otherwise constexpr bool operator==(const iterator& it) const { return _set == it._set and _i == it._i; } @@ -547,7 +546,7 @@ public: /// /// \brief iterator inequality operator /// \param it the iterator to compare with - /// \returns \f$true\f$ if the iterators are different, \f$false\f$ otherwise + /// \returns \emph{true} if the iterators are different, \emph{false} otherwise constexpr bool operator!=(const iterator& it) const { return _set != it._set or _i != it._i; } diff --git a/include/fennec/containers/tuple.h b/include/fennec/containers/tuple.h index ddb6584..434da9e 100644 --- a/include/fennec/containers/tuple.h +++ b/include/fennec/containers/tuple.h @@ -42,20 +42,19 @@ namespace fennec /// /// \brief Tuple, holds a collection of values of different types /// \details -/// | Property | Value | -/// |:-----------:|:----------:| -/// | stable | ⛔ | -/// | dynamic | ✅ | -/// | homogeneous | ⛔ | -/// | distinct | ⛔ | -/// | ordered | ⛔ | -/// | space | \f$O(N)\f$ | -/// | linear | ✅ | -/// | access | \f$O(1)\f$ | -/// | find | \f$O(1)\f$ | -/// | insertion | ⛔ | -/// | deletion | ⛔ | -/// | space | \f$O(N)\f$ | +/// | Property | Value | +/// |:-----------:|:-----------:| +/// | stable | ⛔ | +/// | dynamic | ✅ | +/// | homogeneous | ⛔ | +/// | distinct | ⛔ | +/// | ordered | ⛔ | +/// | linear | ✅ | +/// | space | \emph{O(N)} | +/// | access | \emph{O(1)} | +/// | find | \emph{O(1)} | +/// | insertion | ⛔ | +/// | deletion | ⛔ | /// /// \tparam TypesT The types to store template struct tuple; @@ -65,7 +64,7 @@ template struct tuple; /// \tparam i the index /// \tparam TypesT the types held in the tuple /// \param x the tuple -/// \returns the \f$i\f$th element of the tuple +/// \returns the \emph{i}th element of the tuple template constexpr typename tuple::template elem_t& get(tuple& x) { using elem_t = typename tuple::template elem_t; @@ -77,7 +76,7 @@ constexpr typename tuple::template elem_t& get(tuple& x /// \tparam i the index /// \tparam TypesT the types held in the tuple /// \param x the tuple -/// \returns the \f$i\f$th element of the tuple +/// \returns the \emph{i}th element of the tuple template constexpr const typename tuple::template elem_t& get(const tuple& x) { using elem_t = typename tuple::template elem_t; @@ -98,7 +97,7 @@ public: using base_t = detail::_tuple, TypesT...>; //!< the base type template - using elem_t = typename nth_element::type; //!< helper for getting the \f$i\f$th element + using elem_t = typename nth_element::type; //!< helper for getting the \emph{i}th element static constexpr size_t size = sizeof...(TypesT); //!< the number of elements held by the tuple @@ -114,7 +113,7 @@ public: /// \param args The arguments to initialize the tuple with /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// template tuple(ArgsT&&...args) @@ -126,7 +125,7 @@ public: /// \param cpy the tuple to copy /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// tuple(const tuple& cpy) : base_t(cpy) { @@ -137,7 +136,7 @@ public: /// \param mov the tuple to move /// /// \par Complexity - /// \f$O(N)\f$ + /// \emph{O(N)} /// tuple(tuple&& mov) : base_t(fennec::forward(mov)) { diff --git a/include/fennec/containers/variant.h b/include/fennec/containers/variant.h index fcab270..f436cf8 100644 --- a/include/fennec/containers/variant.h +++ b/include/fennec/containers/variant.h @@ -40,22 +40,21 @@ namespace fennec { /// -/// \brief A structure that represents a union between \f$TypesT\ldots\f$ +/// \brief A structure that represents a union between \emph{TypesT\ldots} /// \details -/// | Property | Value | -/// |:-----------:|:----------:| -/// | stable | ✅ | -/// | dynamic | ⛔ | -/// | homogeneous | ⛔ | -/// | distinct | ⛔ | -/// | ordered | ⛔ | -/// | space | \f$O(N)\f$ | -/// | linear | ⛔ | -/// | access | \f$O(1)\f$ | -/// | find | ⛔ | -/// | insertion | \f$O(1)\f$ | -/// | deletion | \f$O(1)\f$ | -/// | space | \f$O(1)\f$ | +/// | Property | Value | +/// |:-----------:|:-----------:| +/// | stable | ✅ | +/// | dynamic | ⛔ | +/// | homogeneous | ⛔ | +/// | distinct | ⛔ | +/// | ordered | ⛔ | +/// | linear | ⛔ | +/// | space | \emph{O(1)} | +/// | access | \emph{O(1)} | +/// | find | ⛔ | +/// | insertion | \emph{O(1)} | +/// | deletion | \emph{O(1)} | /// /// \tparam TypesT The types to hold in the variant template @@ -90,10 +89,10 @@ public: /// @{ /// - /// \brief Default Constructor, constructs the first type in \f$TypesT\ldots\f$ that is default constructible + /// \brief Default Constructor, constructs the first type in \emph{TypesT...} that is default constructible /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// variant() : _bytes {} @@ -104,13 +103,13 @@ public: } /// - /// \brief Conversion Constructor, constructs the type in \f$TypesT\ldots\f$ that is identical to \f$T\f$ - /// or the first that is constructible with \f$T\f$ + /// \brief Conversion Constructor, constructs the type in \emph{TypesT...} that is identical to \emph{T} + /// or the first that is constructible with \emph{T} /// \tparam T The type of the value /// \param t The value to forward /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// template variant(T&& t) @@ -124,12 +123,12 @@ public: } /// - /// \brief Emplace Constructor, constructs a type \f$T\f$ that is in \f$TypesT\ldots\f$ that is constructible with \f$ArgsT\ldots\f$ + /// \brief Emplace Constructor, constructs a type \emph{T} that is in \emph{TypesT...} that is constructible with \emph{ArgsT...} /// \tparam ArgsT The arguments of the constructor /// \param args The argument values /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// template variant(type_identity, ArgsT&&...args) @@ -146,7 +145,7 @@ public: /// \param v The variant to copy /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// variant(const variant& v) : _bytes {} @@ -169,7 +168,7 @@ public: /// \param v The variant to move /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// variant(variant&& v) noexcept : _bytes {} @@ -191,7 +190,7 @@ public: /// \brief Destructor, if a type is held, destruct it. /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// ~variant() { _clear(); @@ -211,10 +210,10 @@ public: /// \brief value assignment operator /// \tparam T The type to assign /// \param t the value to assign - /// \returns a reference to \f$self\f$ after assigning \f$t\f$ + /// \returns a reference to \emph{self} after assigning \emph{t} /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// template variant& operator=(T&& t) { @@ -259,7 +258,7 @@ public: /// \param args the argument values /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// template requires(contains_element_v) void emplace(ArgsT&&...args) { @@ -273,7 +272,7 @@ public: /// \param args the argument values /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// template void emplace(ArgsT&&...args) { @@ -291,12 +290,12 @@ public: /// @{ /// - /// \brief get the value of the variant interpreted as \f$T\f$ + /// \brief get the value of the variant interpreted as \emph{T} /// \tparam T the type to interpret as - /// \returns The value interpreted as \f$T\f$ + /// \returns The value interpreted as \emph{T} /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// template requires(contains_element_v) T& get() { @@ -305,10 +304,10 @@ public: /// /// \tparam T the type to interpret as - /// \returns The value interpreted as \f$T\f$ + /// \returns The value interpreted as \emph{T} /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// template requires(contains_element_v) const T& get() const { @@ -317,10 +316,10 @@ public: /// /// \tparam T the type to interpret as - /// \returns The value interpreted as \f$T\f$ + /// \returns The value interpreted as \emph{T} /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// template> requires(contains_element_v) T& get() { @@ -329,10 +328,10 @@ public: /// /// \tparam T the type to interpret as - /// \returns The value interpreted as \f$T\f$ + /// \returns The value interpreted as \emph{T} /// /// \par Complexity - /// \f$O(1)\f$ + /// \emph{O(1)} /// template> requires(contains_element_v) const T& get() const { diff --git a/include/fennec/core/logger.h b/include/fennec/core/logger.h index ea770c3..eda8e9e 100644 --- a/include/fennec/core/logger.h +++ b/include/fennec/core/logger.h @@ -32,9 +32,11 @@ #ifndef FENNEC_CORE_LOGGER_H #define FENNEC_CORE_LOGGER_H +#include #include #include #include +#include namespace fennec { @@ -43,6 +45,31 @@ namespace fennec /// \brief logger class class logger : public singleton { +// Definitions ========================================================================================================= +public: + + /// + /// \brief Log Severities + enum severity : uint32_t { + info = 0, + alert, + warning, + error, + fatal, + }; + + static const pair& severity_color(uint32_t severity) { + static constexpr pair colors[] = { + { "\033[0m", "\033[0m" }, // severity_info + { "\033[36m", "\033[0m" }, // severity_alert + { "\033[33m", "\033[0m" }, // severity_warning + { "\033[31m", "\033[0m" }, // severity_error + { "\033[1;31m", "\033[0m" }, // severity_fatal + }; + return colors[severity]; + } + + // Logger System Interface ============================================================================================= public: @@ -54,7 +81,8 @@ public: /// \param str the string to log /// \param _line the line of the log call /// \param _file the file log was called in - static void log(const cstring& str, + static void log(uint32_t severity, + const cstring& str, uint32_t _line = FENNEC_BUILTIN_LINE(), const char* _file = FENNEC_BUILTIN_FILE() ) { @@ -66,9 +94,12 @@ public: inst._logfile.println(str); } + const auto& color = severity_color(severity); + inst._cout->print(color.first); inst._cout->print(cstring(_file, strlen(_file))); inst._cout->printf("({}): ", _line); - inst._cout->println(str); + inst._cout->print(str); + inst._cout->println(color.second); } /// @@ -76,7 +107,8 @@ public: /// \param str the string to log /// \param _line the line of the log call /// \param _file the file log was called in - static void log(const string& str, + static void log(uint32_t severity, + const string& str, uint32_t _line = FENNEC_BUILTIN_LINE(), const char* _file = FENNEC_BUILTIN_FILE() ) { @@ -88,9 +120,13 @@ public: inst._logfile.println(str); } + + const auto& color = severity_color(severity); + inst._cout->print(color.first); inst._cout->print(cstring(_file, strlen(_file))); inst._cout->printf("({}): ", _line); - inst._cout->println(str); + inst._cout->print(str); + inst._cout->println(color.second); } /// @} diff --git a/include/fennec/core/version.h b/include/fennec/core/version.h index 106cd44..f92d768 100644 --- a/include/fennec/core/version.h +++ b/include/fennec/core/version.h @@ -37,6 +37,12 @@ #pragma GCC diagnostic ignored "-Wpedantic" #endif +#if FENNEC_COMPILER_CLANG +#pragma clang diagnostic push +#pragma clang diagnostic ignored "-Wgnu-anonymous-struct" +#pragma clang diagnostic ignored "-Wnested-anon-types" +#endif + #if FENNEC_COMPILER_MSVC #pragma warning(push) #pragma warning(disable:4201) @@ -59,13 +65,13 @@ public: /// @{ union { - uint64_t num; //!< long version number struct { uint16_t major = { 1 }; //!< the major version uint16_t minor = { 0 }; //!< the minor version uint16_t patch = { 0 }; //!< the patch version uint16_t meta = { 0 }; //!< the meta version, e.g. "rc.1" }; + uint64_t num; //!< long version number }; /// @} @@ -114,6 +120,10 @@ public: #pragma GCC diagnostic pop #endif +#ifdef FENNEC_COMPILER_CLANG +#pragma clang diagnostic pop +#endif + #if FENNEC_COMPILER_MSVC #pragma warning(pop) #endif diff --git a/include/fennec/filesystem/file.h b/include/fennec/filesystem/file.h index 611ba86..d0cfd6f 100644 --- a/include/fennec/filesystem/file.h +++ b/include/fennec/filesystem/file.h @@ -39,19 +39,19 @@ namespace fennec /// Flags /// Description /// -/// \f$read\f$ +/// \emph{read} /// Opens file as read-only, reading from start /// -/// \f$write\f$ +/// \emph{write} /// Opens file as write-only, writing to end /// -/// \f$read | write\f$ +/// \emph{read | write} /// Opens file as read-write, reading from start /// -/// \f$write | trunc\f$ +/// \emph{write | trunc} /// Opens file as write-only, destroying contents /// -/// \f$read | write | trunc\f$ +/// \emph{read | write | trunc} /// Opens file as read-write, destroying contents /// enum fmode_ : uint8_t @@ -147,7 +147,7 @@ public: file(); /// - /// \details Initializes a stream pointing to \f$path\f$ opened with \f$mode\f$ + /// \details Initializes a stream pointing to \emph{path} opened with \emph{mode} /// \param path the path of the file /// \param mode the mode to open with file(const cstring& path, uint8_t mode) @@ -156,7 +156,7 @@ public: } /// - /// \details Initializes a stream pointing to \f$path\f$ opened with \f$mode\f$ + /// \details Initializes a stream pointing to \emph{path} opened with \emph{mode} /// \param path the path of the file /// \param mode the mode to open with file(const string& path, uint8_t mode) @@ -166,7 +166,7 @@ public: /// /// \brief Path constructor - /// \details Initializes a stream pointing to \f$path\f$ opened with \f$mode\f$ + /// \details Initializes a stream pointing to \emph{path} opened with \emph{mode} /// \param path the path of the file /// \param mode the mode to open with file(const path& path, uint8_t mode) @@ -179,23 +179,39 @@ public: /// \param file the stream to take ownership of file(file&& file) noexcept; + /// + /// \brief Copy Constructor + /// \details Deleted, no semantics for copying a stream. Holding multiple copies of a stream will cause conflicts. + file(const file&) = delete; + /// /// \brief Destructor /// \details Flushes and closes an open stream ~file(); + ///@} + + +// Assignment ========================================================================================================== +public: + + /// \name Assignment + /// @{ + + /// /// \brief Move assignment /// \param file the stream to take ownership of file& operator=(file&& file) noexcept; - ///@} - -private: - // don't allow copying streams - file(const file&) = delete; + /// + /// \brief Copy Assignment + /// \details Deleted, no semantics for copying a stream. Holding multiple copies of a stream will cause conflicts. + /// \returns Deleted file& operator=(const file&) = delete; + /// @} + // Properties ========================================================================================================== public: @@ -216,7 +232,7 @@ public: } /// - /// \returns \f$true\f$ if there is a valid, open stream. + /// \returns \emph{true} if there is a valid, open stream. bool is_open() const { return _handle != nullptr; } @@ -233,30 +249,30 @@ public: /// /// \param path the path to the file /// \param mode the mode flags to open the file with - /// \returns \f$false\f$ on success, \f$true\f$ on error + /// \returns \emph{false} on success, \emph{true} on error bool open(const cstring& path, uint8_t mode); /// /// \param path the path to the file /// \param mode the mode flags to open the file with - /// \returns \f$false\f$ on success, \f$true\f$ on error + /// \returns \emph{false} on success, \emph{true} on error bool open(const string& path, uint8_t mode); /// /// \brief Open a file /// \param path the path to the file /// \param mode the mode flags to open the file with - /// \returns \f$false\f$ on success, \f$true\f$ on error + /// \returns \emph{false} on success, \emph{true} on error bool open(const path& path, uint8_t mode); /// /// \brief Close a stream - /// \returns \f$false\f$ on success, \f$true\f$ on error + /// \returns \emph{false} on success, \emph{true} on error bool close(); /// /// \brief Commit the streams buffer to the file - /// \returns \f$false\f$ on success, \f$true\f$ on error + /// \returns \emph{false} on success, \emph{true} on error bool commit(); /// @} @@ -270,12 +286,12 @@ public: /// /// \brief closes the stream and erases the file - /// \returns \f$false\f$ on success, \f$true\f$ on error + /// \returns \emph{false} on success, \emph{true} on error bool erase(); /// /// \param path the new path - /// \returns \f$false\f$ on success, \f$true\f$ on error + /// \returns \emph{false} on success, \emph{true} on error /// /// \details /// Copies contents to the new path, and erases the old file. @@ -288,7 +304,7 @@ public: /// /// \param path the new path - /// \returns \f$false\f$ on success, \f$true\f$ on error + /// \returns \emph{false} on success, \emph{true} on error /// /// \details /// Copies contents to the new path, and erases the old file. @@ -302,7 +318,7 @@ public: /// /// \brief Rebind the stream. /// \param path the new path - /// \returns \f$false\f$ on success, \f$true\f$ on error + /// \returns \emph{false} on success, \emph{true} on error /// /// \details /// Copies contents to the new path, and erases the old file. @@ -366,16 +382,16 @@ public: /// /// \param i the new index to move to - /// \returns \f$false\f$ on success, \f$true\f$ otherwise + /// \returns \emph{false} on success, \emph{true} otherwise bool set_pos(size_t i); /// /// \brief return to the start of the stream - /// \returns \f$false\f$ on success, \f$true\f$ otherwise + /// \returns \emph{false} on success, \emph{true} otherwise bool rewind(); /// - /// \returns \f$true\f$ if the stream has reached the end of the file, \f$false\f$ otherwise + /// \returns \emph{true} if the stream has reached the end of the file, \emph{false} otherwise bool eof() const; /// @} @@ -429,13 +445,13 @@ public: /// /// \brief put a character at the current position in the stream /// \param c the character to put - /// \returns \f$false\f$ on success, \f$true\f$ otherwise + /// \returns \emph{false} on success, \emph{true} otherwise bool putc(char c); /// /// \brief put a wide character at the current position in the stream /// \param c the character to put - /// \returns \f$false\f$ on success, \f$true\f$ otherwise + /// \returns \emph{false} on success, \emph{true} otherwise bool putwc(wchar_t c); /// @@ -551,7 +567,7 @@ public: /// \param args the argument values template void printf(const cstring& str, ArgsT&&...args) { - string fmt = fennec::format(str, fennec::forward(args)...); + const string fmt = fennec::format(str, fennec::forward(args)...); this->print(cstring(fmt.cstr(), fmt.length())); } diff --git a/include/fennec/filesystem/path.h b/include/fennec/filesystem/path.h index 5d7fffc..c027e8d 100644 --- a/include/fennec/filesystem/path.h +++ b/include/fennec/filesystem/path.h @@ -115,7 +115,7 @@ public: /// /// \brief C-String Assignment Operator /// \param str the cstring to assign - /// \returns a reference to \f$this\f$ after assigning \f$p\f$ + /// \returns a reference to \emph{this} after assigning \emph{p} template path& operator=(const char (&str)[n]) { _str = str; @@ -125,7 +125,7 @@ public: /// /// \brief C-String Assignment Operator /// \param p the cstring to assign - /// \returns a reference to \f$this\f$ after assigning \f$p\f$ + /// \returns a reference to \emph{this} after assigning \emph{p} path& operator=(const cstring& p) { _str = p; return *this; @@ -134,7 +134,7 @@ public: /// /// \brief String Assignment Operator /// \param p the cstring to assign - /// \returns a reference to \f$this\f$ after assigning \f$p\f$ + /// \returns a reference to \emph{this} after assigning \emph{p} path& operator=(const string& p) { _str = p; return *this; @@ -143,7 +143,7 @@ public: /// /// \brief Path Copy Assignment Operator /// \param p the path to copy - /// \returns a reference to \f$this\f$ after copying \f$p\f$ + /// \returns a reference to \emph{this} after copying \emph{p} path& operator=(const path& p) { _str = p._str; return *this; @@ -152,7 +152,7 @@ public: /// /// \brief Path Move Assignment Operator /// \param p the path to take ownership of - /// \returns a reference to \f$this\f$ after taking ownership of \f$p\f$ + /// \returns a reference to \emph{this} after taking ownership of \emph{p} path& operator=(path&& p) noexcept { _str = move(p._str); return *this; @@ -170,7 +170,7 @@ public: /// /// \brief path equality operator /// \param p the path to compare against - /// \returns \f$true\f$ if the paths are identical, \f$false\f$ otherwise. relative paths are not resolved + /// \returns \emph{true} if the paths are identical, \emph{false} otherwise. relative paths are not resolved bool operator==(const path& p) const { return _str == p._str; } @@ -187,7 +187,7 @@ public: /// /// \brief path append operator /// \param str the filename to append - /// \returns a path containing the current path followed by \f$str\f$ + /// \returns a path containing the current path followed by \emph{str} path operator/(const cstring& str) const { return path(_str + '/' + str); } @@ -195,7 +195,7 @@ public: /// /// \brief path append operator /// \param str the filename to append - /// \returns a path containing the current path followed by \f$str\f$ + /// \returns a path containing the current path followed by \emph{str} path operator/(const string& str) const { return path(_str + '/' + str); } @@ -203,7 +203,7 @@ public: /// /// \brief path append operator /// \param p the path to append - /// \returns a path containing the current path followed by \f$p\f$ + /// \returns a path containing the current path followed by \emph{p} path operator/(const path& p) const { return path(_str + '/' + p._str); } @@ -214,7 +214,7 @@ public: /// \brief the filename of the current path /// \returns a string containing a copy of the filename string filename() const { - size_t i = _str.rfind('/'); + const size_t i = _str.rfind('/'); return _str.substring(i + 1); } @@ -227,9 +227,9 @@ public: const char* cstr() const { return _str.cstr(); } /// - /// \returns \f$true\f$ if the path is empty or points to root + /// \returns \emph{true} if the path is empty or points to root bool is_empty() { - size_t size = _str.size(); + const size_t size = _str.size(); if (size == 0) return true; #if FENNEC_PLATFORM_WINDOWS return (_str[1] == ':' && size == 3); @@ -322,21 +322,21 @@ public: /// @{ /// - /// \brief C++ Iterator Specification \f$begin()\f$ + /// \brief C++ Iterator Specification \emph{begin()} /// \returns an iterator at the first filename in the path iterator begin() const { return iterator(this, 0); } /// - /// \brief C++ Iterator Specification \f$end()\f$ + /// \brief C++ Iterator Specification \emph{end()} /// \returns an iterator to the end of the path iterator end() const { return iterator(this, _str.size()); } /// - /// \brief C++ Iterator Specification \f$iterator\f$ + /// \brief C++ Iterator Specification \emph{iterator} class iterator { public: /// @@ -363,7 +363,7 @@ public: /// /// \brief prefix increment operator - /// \returns \f$self\f$ after having moved to the next element in the list + /// \returns \emph{self} after having moved to the next element in the list constexpr iterator& operator++() { _pos = min(_str->find('/', _pos) + 1, _str->size()); return *this; @@ -371,9 +371,9 @@ public: /// /// \brief postfix increment operator - /// \returns \f$self\f$ before having moved to the next element in the list + /// \returns \emph{self} before having moved to the next element in the list constexpr iterator operator++(int) { - iterator it = *this; + const iterator it = *this; this->operator++(); return it; } @@ -381,7 +381,7 @@ public: /// /// \brief iterator equality operator /// \param rhs the iterator to compare with - /// \returns \f$true\f$ if the iterators are identical, \f$false\f$ otherwise + /// \returns \emph{true} if the iterators are identical, \emph{false} otherwise constexpr bool operator==(const iterator& rhs) const { return _str == rhs._str and _pos == rhs._pos; } @@ -389,7 +389,7 @@ public: /// /// \brief iterator inequality operator /// \param rhs the iterator to compare with - /// \returns \f$true\f$ if the iterators are different, \f$false\f$ otherwise + /// \returns \emph{true} if the iterators are different, \emph{false} otherwise constexpr bool operator!=(const iterator& rhs) const { return _str != rhs._str or _pos != rhs._pos; } diff --git a/include/fennec/format/format.h b/include/fennec/format/format.h index b328317..79f5099 100644 --- a/include/fennec/format/format.h +++ b/include/fennec/format/format.h @@ -60,6 +60,8 @@ string format(const cstring& str, ArgsT&&...args) { .type = '\0', }; + static_assert(argc > 0, "fennec::format may not accept 0 arguments"); + // empty case if constexpr(argc == 0) { return str; diff --git a/include/fennec/format/formatter.h b/include/fennec/format/formatter.h index e9f25cb..e61c187 100644 --- a/include/fennec/format/formatter.h +++ b/include/fennec/format/formatter.h @@ -48,9 +48,9 @@ struct formatter { /// /// \brief default format function /// - /// \details throws a static assertion + /// \details Fails an assertion, the formatter is not implemented for the provided type /// \returns empty string - string operator()(const format_arg&, const T&) { + string operator()(const format_arg&, const T&) const { static_assert(false, "Formatter not implemented for the provided type."); return string(""); } @@ -59,6 +59,8 @@ struct formatter { // strings ============================================================================================================= +// TODO: String formatting + /// /// \brief formatter of a character array /// \tparam N the number of characters @@ -67,8 +69,8 @@ struct formatter { /// /// \brief format function /// \param str the string argument - /// \returns the formatted version of \f$str\f$ - string operator()(const format_arg&, const char (&str)[N]) { + /// \returns the formatted version of \emph{str} + string operator()(const format_arg&, const char (&str)[N]) const { return string(str); } }; @@ -81,8 +83,8 @@ struct formatter { /// /// \brief format function /// \param str the string argument - /// \returns the formatted version of \f$str\f$ - string operator()(const format_arg&, const char (&str)[N]) { + /// \returns the formatted version of \emph{str} + string operator()(const format_arg&, const char (&str)[N]) const { return string(str); } }; @@ -94,8 +96,8 @@ struct formatter { /// /// \brief format function /// \param str the string argument - /// \returns the formatted version of \f$str\f$ - string operator()(const format_arg&, const cstring& str) { + /// \returns the formatted version of \emph{str} + string operator()(const format_arg&, const cstring& str) const { return str; } }; @@ -107,8 +109,8 @@ struct formatter { /// /// \brief format function /// \param str the string argument - /// \returns the formatted version of \f$str\f$ - string operator()(const format_arg&, const string& str) { + /// \returns the formatted version of \emph{str} + string operator()(const format_arg&, const string& str) const { return str; } }; @@ -124,12 +126,12 @@ struct formatter { /// \brief format function /// \param fmt the format specification /// \param x the integral argument - /// \returns the formatted version of \f$x\f$ - string operator()(const format_arg& fmt, IntT x) { + /// \returns the formatted version of \emph{x} + string operator()(const format_arg& fmt, IntT x) const { char digits[128] = {}; auto chk = fennec::to_chars(digits, digits + sizeof(digits), fennec::abs(x), fmt.base); assertf(chk != nullptr, "fennec::format error, to_chars error"); - size_t len = chk - digits; + const size_t len = chk - digits; // handle uppercase if (fmt.upper) { @@ -163,8 +165,8 @@ struct formatter { memset(res.data(), fmt.fill, explen - len); break; case '^': - size_t bef = fill / 2 + has_sign + prefix; - size_t aft = explen - bef; + const size_t bef = fill / 2 + has_sign + prefix; + const size_t aft = explen - bef; memcpy(res.data() + bef, digits, len); sign = fmt.fill == '0' ? 0 : bef - 1 - prefix; memset(res.data(), fmt.fill, bef); @@ -200,8 +202,8 @@ struct formatter { /// \brief format function /// \param fmt the format specification /// \param x the boolean argument - /// \returns the formatted version of \f$x\f$ - string operator()(const format_arg& fmt, BoolT x) { + /// \returns the formatted version of \emph{x} + string operator()(const format_arg& fmt, BoolT x) const { if (fmt.type == 's' or fmt.type == '\0') { return x ? string("true") : string("false"); } @@ -218,8 +220,8 @@ struct formatter { /// \brief format function /// \param fmt the format specification /// \param x the float argument - /// \returns the formatted version of \f$x\f$ - string operator()(const format_arg& fmt, FloatT x) { + /// \returns the formatted version of \emph{x} + string operator()(const format_arg& fmt, FloatT x) const { // nan & inf cases if (fennec::isnan(x)) { @@ -267,8 +269,8 @@ struct formatter { memset(res.data(), fmt.fill, explen - len); break; case '^': - size_t bef = fill / 2 + has_sign + prefix; - size_t aft = explen - bef; + const size_t bef = fill / 2 + has_sign + prefix; + const size_t aft = explen - bef; memcpy(res.data() + bef, digits, len); sign = fmt.fill == '0' ? 0 : bef - 1 - prefix; memset(res.data(), fmt.fill, bef); diff --git a/include/fennec/interpret/tokenizer.h b/include/fennec/interpret/tokenizer.h index b980315..7fd4517 100644 --- a/include/fennec/interpret/tokenizer.h +++ b/include/fennec/interpret/tokenizer.h @@ -94,8 +94,8 @@ private: list res; priority_queue> idx; - for (char c : delimiter) { - size_t i = 0; + for (const char c : delimiter) { + const size_t i = 0; while (i != line.size()) { size_t n = line.find(c, i); // TODO diff --git a/include/fennec/lang/assert.h b/include/fennec/lang/assert.h index 9f4bf88..ecedfbc 100644 --- a/include/fennec/lang/assert.h +++ b/include/fennec/lang/assert.h @@ -48,18 +48,18 @@ ///
/// assert(expr, desc) /// -/// Make an assertion with expression \f$expr\f$ and provide a description \f$desc\f$. Only halts in debug mode. +/// Make an assertion with expression \emph{expr} and provide a description \emph{desc}. Only halts in debug mode. /// ///
/// assertf(expr, desc) /// -/// Make an assertion with expression \f$expr\f$ and provide a description \f$desc\f$. Always halts. +/// Make an assertion with expression \emph{expr} and provide a description \emph{desc}. Always halts. /// ///
/// assertd(expr, desc) /// -/// Make an assertion, ***only in debug mode***, with expression \f$expr\f$ and provide a description \f$desc\f$. -/// This should be used when the branching caused by \f$assert\f$ would hinder performance in release mode. +/// Make an assertion, ***only in debug mode***, with expression \emph{expr} and provide a description \emph{desc}. +/// This should be used when the branching caused by \emph{assert} would hinder performance in release mode. /// /// /// @@ -92,7 +92,7 @@ void _assert(const char (&expr)[ExprL], /// \param description the description of the assertion #define assert(expression, description) \ if(not(expression)) [[unlikely]] { \ - _assert(#expression, __FILE__, __LINE__, __PRETTY_FUNCTION__, description, not FENNEC_RELEASE); \ + _assert(#expression, __FILE__, __LINE__, __PRETTY_FUNCTION__, description, FENNEC_DEBUG); \ } /// diff --git a/include/fennec/lang/bits.h b/include/fennec/lang/bits.h index fe5b871..3217a03 100644 --- a/include/fennec/lang/bits.h +++ b/include/fennec/lang/bits.h @@ -116,7 +116,7 @@ constexpr ToT bit_cast(const FromT& from) { /// \param arr the array of bytes to modify /// \param mask the mask to and against arr /// \param n the number of bytes -/// \returns the pointer \f$arr\f$ +/// \returns the pointer \emph{arr} constexpr void* bit_and(void* arr, const void* mask, size_t n) { if (arr == mask) { return arr; diff --git a/include/fennec/lang/compare.h b/include/fennec/lang/compare.h index bfa5cca..4757789 100644 --- a/include/fennec/lang/compare.h +++ b/include/fennec/lang/compare.h @@ -33,23 +33,23 @@ namespace fennec template struct equality; /// -/// \brief Implementations for two types that have a common equality operator \f$==\f$ +/// \brief Implementations for two types that have a common equality operator \math{=} /// \tparam T0 The first type /// \tparam T1 The second type template requires has_equals_v struct equality { /// /// \brief operator to test the two values - /// \param x the value of type \f$T0\f$ - /// \param y the value of type \f$T1\f$ - /// \returns \f$true\f$ if equal, \f$false\f$ otherwise + /// \param x the value of type \emph{T0} + /// \param y the value of type \emph{T1} + /// \returns \emph{true} if equal, \emph{false} otherwise constexpr bool operator()(const T0& x, const T1& y) const { return x == y; } }; /// -/// \brief Implementations for two types that have a common less operator \f$<\f$ +/// \brief Implementations for two types that have a common less operator \math{<} /// \tparam T0 The first type /// \tparam T1 The second type template requires(not has_equals_v @@ -57,16 +57,16 @@ template requires(not has_equals_v struct equality { /// /// \brief operator to test the two values - /// \param x the value of type \f$T0\f$ - /// \param y the value of type \f$T1\f$ - /// \returns \f$true\f$ if equal, \f$false\f$ otherwise + /// \param x the value of type \emph{T0} + /// \param y the value of type \emph{T1} + /// \returns \emph{true} if equal, \emph{false} otherwise constexpr bool operator()(const T0& x, const T1& y) const { return not(x < y) and not(y < x); } }; /// -/// \brief Implementations for two types that have a common greater operator \f$>\f$ +/// \brief Implementations for two types that have a common greater operator \math{>} /// \tparam T0 The first type /// \tparam T1 The second type template requires(not(has_equals_v) @@ -75,9 +75,9 @@ template requires(not(has_equals_v) struct equality { /// /// \brief operator to test the two values - /// \param x the value of type \f$T0\f$ - /// \param y the value of type \f$T1\f$ - /// \returns \f$true\f$ if equal, \f$false\f$ otherwise + /// \param x the value of type \emph{T0} + /// \param y the value of type \emph{T1} + /// \returns \emph{true} if equal, \emph{false} otherwise constexpr bool operator()(const T0& x, const T1& y) const { return not(x > y) and not(y > x); } @@ -93,16 +93,16 @@ struct equality { template struct inequality; /// -/// \brief Implementations for two types that have a common inequality operator \f$\neq\f$ +/// \brief Implementations for two types that have a common inequality operator \math{\neq} /// \tparam T0 The first type /// \tparam T1 The second type template requires has_nequals_v struct inequality { /// /// \brief operator to test the two values - /// \param x the value of type \f$T0\f$ - /// \param y the value of type \f$T1\f$ - /// \returns \f$true\f$ if not equal, \f$false\f$ otherwise + /// \param x the value of type \emph{T0} + /// \param y the value of type \emph{T1} + /// \returns \emph{true} if not equal, \emph{false} otherwise constexpr bool operator()(const T0& x, const T1& y) const { return x != y; } @@ -110,48 +110,48 @@ struct inequality { /// -/// \brief Implementations for two types that have a common equality operator \f$==\f$ +/// \brief Implementations for two types that have a common equality operator \math{=} /// \tparam T0 The first type /// \tparam T1 The second type template requires has_equals_v struct inequality { /// /// \brief operator to test the two values - /// \param x the value of type \f$T0\f$ - /// \param y the value of type \f$T1\f$ - /// \returns \f$true\f$ if not equal, \f$false\f$ otherwise + /// \param x the value of type \emph{T0} + /// \param y the value of type \emph{T1} + /// \returns \emph{true} if not equal, \emph{false} otherwise constexpr bool operator()(const T0& x, const T1& y) const { return not (x == y); } }; /// -/// \brief Implementations for two types that have a common less operator \f$<\f$ +/// \brief Implementations for two types that have a common less operator \math{<} /// \tparam T0 The first type /// \tparam T1 The second type template requires has_less_v and has_less_v struct inequality { /// /// \brief operator to test the two values - /// \param x the value of type \f$T0\f$ - /// \param y the value of type \f$T1\f$ - /// \returns \f$true\f$ if not equal, \f$false\f$ otherwise + /// \param x the value of type \emph{T0} + /// \param y the value of type \emph{T1} + /// \returns \emph{true} if not equal, \emph{false} otherwise constexpr bool operator()(const T0& x, const T1& y) const { return (x < y) or (y < x); } }; /// -/// \brief Implementations for two types that have a common greater operator \f$>\f$ +/// \brief Implementations for two types that have a common greater operator \math{>} /// \tparam T0 The first type /// \tparam T1 The second type template requires has_greater_v and has_greater_v struct inequality { /// /// \brief operator to test the two values - /// \param x the value of type \f$T0\f$ - /// \param y the value of type \f$T1\f$ - /// \returns \f$true\f$ if not equal, \f$false\f$ otherwise + /// \param x the value of type \emph{T0} + /// \param y the value of type \emph{T1} + /// \returns \emph{true} if not equal, \emph{false} otherwise constexpr bool operator()(const T0& x, const T1& y) const { return (x > y) or (y > x); } @@ -161,16 +161,16 @@ struct inequality { // less ================================================================================================================ /// -/// \brief Struct to test if a value of type \f$T0\f$ is less than a value of type \f$T1\f$ +/// \brief Struct to test if a value of type \emph{T0} is less than a value of type \emph{T1} /// \tparam T0 The first type /// \tparam T1 The second type template requires has_less_v struct less { /// /// \brief operator to test the two values - /// \param x the value of type \f$T0\f$ - /// \param y the value of type \f$T1\f$ - /// \returns \f$true\f$ if less, \f$false\f$ otherwise + /// \param x the value of type \emph{T0} + /// \param y the value of type \emph{T1} + /// \returns \emph{true} if less, \emph{false} otherwise constexpr bool operator()(const T0& x, const T1& y) const { return x < y; } @@ -180,16 +180,16 @@ struct less { // less_equal ========================================================================================================== /// -/// \brief Struct to test if a value of type \f$T0\f$ is less than or equal to a value of type \f$T1\f$ +/// \brief Struct to test if a value of type \emph{T0} is less than or equal to a value of type \emph{T1} /// \tparam T0 The first type /// \tparam T1 The second type template requires has_less_equals_v struct less_equals { /// /// \brief operator to test the two values - /// \param x the value of type \f$T0\f$ - /// \param y the value of type \f$T1\f$ - /// \returns \f$true\f$ if less than or equal, \f$false\f$ otherwise + /// \param x the value of type \emph{T0} + /// \param y the value of type \emph{T1} + /// \returns \emph{true} if less than or equal, \emph{false} otherwise constexpr bool operator()(const T0& x, const T1& y) const { return x <= y; } @@ -199,16 +199,16 @@ struct less_equals { // greater ============================================================================================================= /// -/// \brief Struct to test if a value of type \f$T0\f$ is greater than a value of type \f$T1\f$ +/// \brief Struct to test if a value of type \emph{T0} is greater than a value of type \emph{T1} /// \tparam T0 The first type /// \tparam T1 The second type template requires has_greater_v struct greater { /// /// \brief operator to test the two values - /// \param x the value of type \f$T0\f$ - /// \param y the value of type \f$T1\f$ - /// \returns \f$true\f$ if greater, \f$false\f$ otherwise + /// \param x the value of type \emph{T0} + /// \param y the value of type \emph{T1} + /// \returns \emph{true} if greater, \emph{false} otherwise constexpr bool operator()(const T0& x, const T1& y) const { return x > y; } @@ -218,16 +218,16 @@ struct greater { // less_equal ========================================================================================================== /// -/// \brief Struct to test if a value of type \f$T0\f$ is greater than or equal to a value of type \f$T1\f$ +/// \brief Struct to test if a value of type \emph{T0} is greater than or equal to a value of type \emph{T1} /// \tparam T0 The first type /// \tparam T1 The second type template requires has_greater_equals_v struct greater_equals { /// /// \brief operator to test the two values - /// \param x the value of type \f$T0\f$ - /// \param y the value of type \f$T1\f$ - /// \returns \f$true\f$ if greater than or equal, \f$false\f$ otherwise + /// \param x the value of type \emph{T0} + /// \param y the value of type \emph{T1} + /// \returns \emph{true} if greater than or equal, \emph{false} otherwise constexpr bool operator()(const T0& x, const T1& y) const { return x >= y; } diff --git a/include/fennec/lang/conditional_types.h b/include/fennec/lang/conditional_types.h index cbf7dc2..7843da7 100644 --- a/include/fennec/lang/conditional_types.h +++ b/include/fennec/lang/conditional_types.h @@ -77,8 +77,8 @@ namespace fennec /// \details Selects between \p TrueT and \p FalseT based on the boolean value \p b. /// The chosen type is stored in `fennec::conditional::type`. /// \tparam B the value of the condition -/// \tparam TrueT type to use when \f$B == true\f$ -/// \tparam FalseT type to use when \f$B == false\f$ +/// \tparam TrueT type to use when \math{\textbf{B} = \textbf{true}} +/// \tparam FalseT type to use when \math{\textbf{B} = \textbf{false}} template struct conditional; @@ -90,12 +90,12 @@ using conditional_t = typename conditional::type; #ifndef FENNEC_DOXYGEN -// specialization of fennec::conditional for \f$true\f$ case +// specialization of fennec::conditional for \emph{true} case template struct conditional : type_identity{}; -// specialization of fennec::conditional for \f$false\f$ case +// specialization of fennec::conditional for \emph{false} case template struct conditional : type_identity{}; #endif @@ -103,13 +103,13 @@ struct conditional : type_identity{}; // fennec::detect ====================================================================================================== /// -/// \brief Detect whether \f$DetectT\f$ is a valid type +/// \brief Detect whether \emph{DetectT} is a valid type /// -/// \details Selects \f$DetectT\f$ if it exists, otherwise selects \f$DefaultT\f$ The chosen type is stored in `fennec::detect::type` and -/// a boolean value is stored in `fennec::detect::is_detected` representing whether \f$DetectT\f$ is found. +/// \details Selects \emph{DetectT} if it exists, otherwise selects \emph{DefaultT} The chosen type is stored in `fennec::detect::type` and +/// a boolean value is stored in `fennec::detect::is_detected` representing whether \emph{DetectT} is found. /// \tparam DefaultT Default type /// \tparam DetectT Type to detect -/// \tparam ArgsT Any template arguments for \f$DetectT\f$ +/// \tparam ArgsT Any template arguments for \emph{DetectT} template typename DetectT, typename...ArgsT> struct detect { @@ -140,7 +140,7 @@ struct detect /// /// \brief Leverage SFINAE to conditionally enable a function or class at compile-time /// -/// \details If \f$B\f$ is \f$true\f$, define a public member type \f$type\f$. Otherwise, there is no member.
+/// \details If \emph{B} is \emph{true}, define a public member type \emph{type}. Otherwise, there is no member.
/// **Example Usage** /// \code{.cpp} /// template auto declval() noexcept -> decltype(detail::_declval(0)) { static_assert(detail::_declval_protector{}, "declval must not be used"); return detail::_declval(0); diff --git a/include/fennec/lang/detail/_type_traits.h b/include/fennec/lang/detail/_type_traits.h index 9924225..34705a8 100644 --- a/include/fennec/lang/detail/_type_traits.h +++ b/include/fennec/lang/detail/_type_traits.h @@ -19,7 +19,6 @@ #ifndef FENNEC_LANG_DETAIL_TYPE_TRAITS_H #define FENNEC_LANG_DETAIL_TYPE_TRAITS_H -#include #include #include @@ -82,6 +81,12 @@ namespace fennec::detail template struct _is_rvalue_reference : false_type {}; template struct _is_rvalue_reference : true_type {}; + template struct _is_bounded_array : false_type {}; + template struct _is_bounded_array : true_type {}; + + template struct _is_unbounded_array : false_type {}; + template struct _is_unbounded_array : true_type {}; + template struct _is_complete { template static auto test(U*) -> bool_constant; @@ -105,13 +110,37 @@ namespace fennec::detail using type = decltype(test(0)); }; + template + auto _begin(ContainerT& c) noexcept(noexcept(c.begin())) -> decltype(c.begin()) { + return c.begin(); + } + + template + auto _begin(T (&arr)[N]) -> T* { + return arr[0]; + } + + void _begin(...); + + template + auto _end(ContainerT& c) noexcept(noexcept(c.end())) -> decltype(c.end()) { + return c.end(); + } + + template + auto _end(T (&arr)[N]) -> T* { + return arr[N - 1]; + } + + void _end(...); + // https://stackoverflow.com/questions/13830158/how-to-write-a-trait-which-checks-whether-a-type-is-iterable template auto _is_iterable(int) -> decltype( - fennec::begin(declval()) != fennec::end(declval()), + detail::_begin(declval()) != detail::_end(declval()), void(), - ++declval()))&>(), - void(*fennec::begin(declval())), + ++declval()))&>(), + void(*detail::_begin(declval())), true_type{} ); @@ -130,6 +159,20 @@ namespace fennec::detail auto _is_indexable(...) -> false_type; + // https://stackoverflow.com/a/31409532 + template + auto _is_iterator(...) -> decltype( + declval() != declval(), + void(), + ++declval(), + *declval(), + true_type{} + ); + + template + auto _is_iterator(...) -> false_type; + + template auto _is_mappable(int) -> decltype( diff --git a/include/fennec/lang/float.h b/include/fennec/lang/float.h index a1c8fc9..5ecc183 100644 --- a/include/fennec/lang/float.h +++ b/include/fennec/lang/float.h @@ -23,7 +23,7 @@ /// /// \details This file is automatically generated for the current build environment. /// -/// Environment for this build: GNU Linux x86_64 +/// Environment for this build: Clang Linux x86_64 /// /// \copyright Copyright © 2025 - 2026 Medusa Slockbower ([GPLv3](https://www.gnu.org/licenses/gpl-3.0.en.html)) /// @@ -60,55 +60,55 @@ #undef FLT_DENORM_MIN #undef FLT_ROUND_ERR -/// \brief Does \f$float\f$ have an infinity? +/// \brief Does \emph{float} have an infinity? #define FLT_HAS_INFINITY 1 -/// \brief Does \f$float\f$ have a quiet NaN? +/// \brief Does \emph{float} have a quiet NaN? #define FLT_HAS_QUIET_NAN 1 -/// \brief Does \f$float\f$ have a signaling NaN? +/// \brief Does \emph{float} have a signaling NaN? #define FLT_HAS_SIGNALING_NAN 1 -/// \brief Does \f$float\f$ use denormalization? +/// \brief Does \emph{float} use denormalization? #define FLT_HAS_DENORM 1 -/// \brief Does \f$float\f$ have loss with denormalization? +/// \brief Does \emph{float} have loss with denormalization? #define FLT_HAS_DENORM_LOSS 0 -/// \brief What rounding style does \f$float\f$ use? +/// \brief What rounding style does \emph{float} use? #define FLT_ROUNDS 1 -/// \brief Does \f$float\f$ use the IEEE floating point specification? +/// \brief Does \emph{float} use the IEEE floating point specification? #define FLT_IS_IEC559 1 -/// \brief The number of mantissa bits in \f$float\f$. +/// \brief The number of mantissa bits in \emph{float}. #define FLT_MANT_DIG 24 -/// \brief The number of decimal digits guaranteed to be preserved in a \f$float\f$ → \f$text\f$ → \f$float\f$. +/// \brief The number of decimal digits guaranteed to be preserved in a \emph{float} → \emph{text} → \emph{float}. #define FLT_DIG 6 -/// \brief The decimal precision required to serialize and deserialize a \f$float\f$. +/// \brief The decimal precision required to serialize and deserialize a \emph{float}. #define FLT_DECIMAL_DIG 9 -/// \brief The radix, or integer base, used to represent a \f$float\f$. +/// \brief The radix, or integer base, used to represent a \emph{float}. #define FLT_RADIX 2 -/// \brief The minimum negative integer such that \f${FLT_RADIX}^{FLT_MIN_EXP}\f$ results in a normalized \f$float\f$. +/// \brief The minimum negative integer such that \math{\textbf{FLT_RADIX}^\textbf{FLT_MIN_EXP}} results in a normalized \emph{float}. #define FLT_MIN_EXP -125 -/// \brief The maximum positive integer such that \f${FLT_RADIX}^{FLT_MAX_EXP}\f$ results in a non-infinite \f$float\f$. +/// \brief The maximum positive integer such that \math{\textbf{FLT_RADIX}^\textbf{FLT_MAX_EXP}} results in a non-infinite \emph{float}. #define FLT_MAX_EXP 128 -/// \brief The minimum negative integer such that \f${10}^{FLT_MIN_EXP}\f$ results in a normalized \f$float\f$. +/// \brief The minimum negative integer such that \math{{10}^\textbf{FLT_MIN_EXP}} results in a normalized \emph{float}. #define FLT_MIN_10_EXP -37 -/// \brief The maximum positive integer such that \f${10}^{FLT_MAX_EXP}\f$ results in a non-infinite \f$float\f$. +/// \brief The maximum positive integer such that \math{{10}^\textbf{FLT_MAX_EXP}} results in a non-infinite \emph{float}. #define FLT_MAX_10_EXP 38 -/// \brief Do arithmetics operations with \f$float\f$ trap? +/// \brief Do arithmetics operations with \emph{float} trap? #define FLT_TRAPS 0 -/// \brief Do arithmetics operations with \f$float\f$ check for underflow? +/// \brief Do arithmetics operations with \emph{float} check for underflow? #define FLT_TINYNESS_BEFORE 0 -/// \brief Smallest positive, finite, normal value of \f$float\f$. +/// \brief Smallest positive, finite, normal value of \emph{float}. #define FLT_MIN fennec::bit_cast(0x800000) -/// \brief Largest positive, finite value of \f$float\f$. +/// \brief Largest positive, finite value of \emph{float}. #define FLT_MAX fennec::bit_cast(0x7f7fffff) -/// \brief The difference between \f$1.0\f$ and the next representable value of \f$float\f$. +/// \brief The difference between \emph{1.0} and the next representable value of \emph{float}. #define FLT_EPSILON fennec::bit_cast(0x34000000) -/// \brief A value representing \f$\inf\f$ of type \f$float\f$. +/// \brief A value representing \emph{\inf} of type \emph{float}. #define FLT_INF fennec::bit_cast(0x7f800000) -/// \brief A value representing \f$NaN\f$ of type \f$float\f$ that does not trap. +/// \brief A value representing \emph{NaN} of type \emph{float} that does not trap. #define FLT_QUIET_NAN fennec::bit_cast(0x7fc00000) -/// \brief A value representing \f$NaN\f$ of type \f$float\f$ that traps. +/// \brief A value representing \emph{NaN} of type \emph{float} that traps. #define FLT_SIGNALING_NAN fennec::bit_cast(0x7fa00000) -/// \brief Smallest positive, finite, subnormal value of \f$float\f$. +/// \brief Smallest positive, finite, subnormal value of \emph{float}. #define FLT_DENORM_MIN fennec::bit_cast(0x1) -/// \brief Maximum rounding error of type \f$float\f$. +/// \brief Maximum rounding error of type \emph{float}. #define FLT_ROUND_ERR fennec::bit_cast(0x3f000000) #undef DBL_HAS_INFINITY @@ -137,55 +137,55 @@ #undef DBL_DENORM_MIN #undef DBL_ROUND_ERR -/// \brief Does \f$double\f$ have an infinity? +/// \brief Does \emph{double} have an infinity? #define DBL_HAS_INFINITY 1 -/// \brief Does \f$double\f$ have a quiet NaN? +/// \brief Does \emph{double} have a quiet NaN? #define DBL_HAS_QUIET_NAN 1 -/// \brief Does \f$double\f$ have a signaling NaN? +/// \brief Does \emph{double} have a signaling NaN? #define DBL_HAS_SIGNALING_NAN 1 -/// \brief Does \f$double\f$ use denormalization? +/// \brief Does \emph{double} use denormalization? #define DBL_HAS_DENORM 1 -/// \brief Does \f$double\f$ have loss with denormalization? +/// \brief Does \emph{double} have loss with denormalization? #define DBL_HAS_DENORM_LOSS 0 -/// \brief What rounding style does \f$double\f$ use? +/// \brief What rounding style does \emph{double} use? #define DBL_ROUNDS 1 -/// \brief Does \f$double\f$ use the IEEE doubleing point specification? +/// \brief Does \emph{double} use the IEEE doubleing point specification? #define DBL_IS_IEC559 1 -/// \brief The number of mantissa bits in \f$double\f$. +/// \brief The number of mantissa bits in \emph{double}. #define DBL_MANT_DIG 53 -/// \brief The number of decimal digits guaranteed to be preserved in a \f$double\f$ → \f$text\f$ → \f$double\f$. +/// \brief The number of decimal digits guaranteed to be preserved in a \emph{double} → \emph{text} → \emph{double}. #define DBL_DIG 15 -/// \brief The decimal precision required to serialize and deserialize a \f$double\f$. +/// \brief The decimal precision required to serialize and deserialize a \emph{double}. #define DBL_DECIMAL_DIG 17 -/// \brief The radix, or integer base, used to represent a \f$double\f$. +/// \brief The radix, or integer base, used to represent a \emph{double}. #define DBL_RADIX 2 -/// \brief The minimum negative integer such that \f${DBL_RADIX}^{DBL_MIN_EXP}\f$ results in a normalized \f$double\f$. +/// \brief The minimum negative integer such that \math{\textbf{DBL_RADIX}^\textbf{DBL_MIN_EXP}} results in a normalized \emph{double}. #define DBL_MIN_EXP -1021 -/// \brief The maximum positive integer such that \f${DBL_RADIX}^{DBL_MAX_EXP}\f$ results in a non-infinite \f$double\f$. +/// \brief The maximum positive integer such that \math{\textbf{DBL_RADIX}^\textbf{DBL_MAX_EXP}} results in a non-infinite \emph{double}. #define DBL_MAX_EXP 1024 -/// \brief The minimum negative integer such that \f${10}^{DBL_MIN_EXP}\f$ results in a normalized \f$double\f$. +/// \brief The minimum negative integer such that \math{{10}^\textbf{DBL_MIN_EXP}} results in a normalized \emph{double}. #define DBL_MIN_10_EXP -307 -/// \brief The maximum positive integer such that \f${10}^{DBL_MAX_EXP}\f$ results in a non-infinite \f$double\f$. +/// \brief The maximum positive integer such that \math{{10}^\textbf{DBL_MAX_EXP}} results in a non-infinite \emph{double}. #define DBL_MAX_10_EXP 308 -/// \brief Do arithmetics operations with \f$double\f$ trap? +/// \brief Do arithmetics operations with \emph{double} trap? #define DBL_TRAPS 0 -/// \brief Do arithmetics operations with \f$double\f$ check for underflow? +/// \brief Do arithmetics operations with \emph{double} check for underflow? #define DBL_TINYNESS_BEFORE 0 -/// \brief Smallest positive, finite, normal value of \f$double\f$. +/// \brief Smallest positive, finite, normal value of \emph{double}. #define DBL_MIN fennec::bit_cast(0x10000000000000ll) -/// \brief Largest positive, finite value of \f$double\f$. +/// \brief Largest positive, finite value of \emph{double}. #define DBL_MAX fennec::bit_cast(0x7fefffffffffffffll) -/// \brief The difference between \f$1.0\f$ and the next representable value of \f$double\f$. +/// \brief The difference between \emph{1.0} and the next representable value of \emph{double}. #define DBL_EPSILON fennec::bit_cast(0x3cb0000000000000ll) -/// \brief A value representing \f$\inf\f$ of type \f$double\f$. +/// \brief A value representing \emph{\inf} of type \emph{double}. #define DBL_INF fennec::bit_cast(0x7ff0000000000000ll) -/// \brief A value representing \f$NaN\f$ of type \f$double\f$ that does not trap. +/// \brief A value representing \emph{NaN} of type \emph{double} that does not trap. #define DBL_QUIET_NAN fennec::bit_cast(0x7ff8000000000000ll) -/// \brief A value representing \f$NaN\f$ of type \f$double\f$ that traps. +/// \brief A value representing \emph{NaN} of type \emph{double} that traps. #define DBL_SIGNALING_NAN fennec::bit_cast(0x7ff4000000000000ll) -/// \brief Smallest positive, finite, subnormal value of \f$double\f$. +/// \brief Smallest positive, finite, subnormal value of \emph{double}. #define DBL_DENORM_MIN fennec::bit_cast(0x1ll) -/// \brief Maximum rounding error of type \f$double\f$. +/// \brief Maximum rounding error of type \emph{double}. #define DBL_ROUND_ERR fennec::bit_cast(0x3fe0000000000000ll) #endif // FENNEC_LANG_FLOAT_H diff --git a/include/fennec/lang/function.h b/include/fennec/lang/function.h index 4e310c4..12b1aff 100644 --- a/include/fennec/lang/function.h +++ b/include/fennec/lang/function.h @@ -85,18 +85,18 @@ public: /// /// \brief copy assignment /// \param func the function to copy - /// \returns a reference to self + /// \returns a reference to \emph{this} constexpr function& operator=(const function& func) = default; /// /// \brief move assignment /// \param func the function to capture - /// \returns a reference to self + /// \returns a reference to \emph{this} constexpr function& operator=(function&& func) = default; /// /// \brief null assignment - /// \returns a reference to self + /// \returns a reference to \emph{this} constexpr function& operator=(nullptr_t) { call = nullptr; return *this; @@ -105,7 +105,7 @@ public: /// /// \brief function assignment /// \param func the function to capture - /// \returns a reference to self + /// \returns a reference to \emph{this} constexpr function& operator=(ReturnT (*func)(ArgsT...)) { call = func; return *this; @@ -113,7 +113,7 @@ public: /// /// \brief implicit bool check - /// \returns \f$true\f$ if a function is captured, \f$false\f$ otherwise + /// \returns \emph{true} if a function is captured, \emph{false} otherwise constexpr operator bool() const noexcept { return call != nullptr; } diff --git a/include/fennec/lang/hashing.h b/include/fennec/lang/hashing.h index 1c13ded..d6023da 100644 --- a/include/fennec/lang/hashing.h +++ b/include/fennec/lang/hashing.h @@ -66,11 +66,11 @@ struct hash : hash { /// \param ptr the pointer to hash /// \returns an integer hash for the value constexpr size_t operator()(PtrT* ptr) const { - return hash::operator()((uintptr_t)(const void*)ptr); + return hash::operator()(fennec::bit_cast(ptr)); } }; -// Float +/// \brief Hashing for `float` template<> struct hash : hash { using type_t = float; //!< the type of the hash @@ -82,6 +82,7 @@ struct hash : hash { } }; +/// \brief Hashing for `double` template<> struct hash : hash { using type_t = double; //!< the type of the hash diff --git a/include/fennec/lang/integer.h b/include/fennec/lang/integer.h index f263aef..99144db 100644 --- a/include/fennec/lang/integer.h +++ b/include/fennec/lang/integer.h @@ -23,7 +23,7 @@ /// /// \details This file is automatically generated for the current build environment. /// -/// Environment for this build: GNU Linux x86_64 +/// Environment for this build: Clang Linux x86_64 /// /// \copyright Copyright © 2025 - 2026 Medusa Slockbower ([GPLv3](https://www.gnu.org/licenses/gpl-3.0.en.html)) /// @@ -53,212 +53,212 @@ #undef ULLONG_MIN #undef ULLONG_MAX -/// \brief Is \f$char\f$ signed? +/// \brief Is \emph{char} signed? #define CHAR_IS_SIGNED true -/// \brief Rounding style of type \f$char\f$. -#define CHAR_ROUNDS 0x0 -/// \brief Number of radix digits represented by \f$char\f$. +/// \brief Rounding style of type \emph{char}. +#define CHAR_ROUNDS 0 +/// \brief Number of radix digits represented by \emph{char}. #define CHAR_RADIX_DIG 0x7 -/// \brief Number of decimal digits represented by \f$char\f$. +/// \brief Number of decimal digits represented by \emph{char}. #define CHAR_DIG 0x2 -/// \brief Number of decimal digits necessary to differentiate all values of type \f$char\f$. -#define CHAR_DECIMAL_DIG 0x0 -/// \brief The radix, or integer base, used to represent a \f$char\f$. +/// \brief Number of decimal digits necessary to differentiate all values of type \emph{char}. +#define CHAR_DECIMAL_DIG 0 +/// \brief The radix, or integer base, used to represent a \emph{char}. #define CHAR_RADIX 0x2 -/// \brief Do arithmetics operations with \f$char\f$ trap? -#define CHAR_TRAPS 0xtrue -/// \brief Smallest finite value of \f$char\f$. -#define CHAR_MIN 0x80 -/// \brief Largest finite value of \f$char\f$. +/// \brief Do arithmetics operations with \emph{char} trap? +#define CHAR_TRAPS true +/// \brief Smallest finite value of \emph{char}. +#define CHAR_MIN -0x80 +/// \brief Largest finite value of \emph{char}. #define CHAR_MAX 0x7f -/// \brief Is \f$wchar_t\f$ signed? +/// \brief Is \emph{wchar_t} signed? #define WCHAR_IS_SIGNED true -/// \brief Rounding style of type \f$wchar_t\f$. -#define WCHAR_ROUNDS 0x0 -/// \brief Number of radix digits represented by \f$wchar_t\f$. +/// \brief Rounding style of type \emph{wchar_t}. +#define WCHAR_ROUNDS 0 +/// \brief Number of radix digits represented by \emph{wchar_t}. #define WCHAR_RADIX_DIG 0x1f -/// \brief Number of decimal digits represented by \f$wchar_t\f$. +/// \brief Number of decimal digits represented by \emph{wchar_t}. #define WCHAR_DIG 0x9 -/// \brief Number of decimal digits necessary to differentiate all values of type \f$wchar_t\f$. -#define WCHAR_DECIMAL_DIG 0x0 -/// \brief The radix, or integer base, used to represent a \f$wchar_t\f$. +/// \brief Number of decimal digits necessary to differentiate all values of type \emph{wchar_t}. +#define WCHAR_DECIMAL_DIG 0 +/// \brief The radix, or integer base, used to represent a \emph{wchar_t}. #define WCHAR_RADIX 0x2 -/// \brief Do arithmetics operations with \f$wchar_t\f$ trap? -#define WCHAR_TRAPS 0xtrue -/// \brief Smallest finite value of \f$wchar_t\f$. -#define WCHAR_MIN 0x80000000 -/// \brief Largest finite value of \f$wchar_t\f$. -#define WCHAR_MAX 0x7fffffff +/// \brief Do arithmetics operations with \emph{wchar_t} trap? +#define WCHAR_TRAPS true +/// \brief Smallest finite value of \emph{wchar_t}. +#define WCHAR_MIN - 0x0 +/// \brief Largest finite value of \emph{wchar_t}. +#define WCHAR_MAX 0xffff -/// \brief Is \f$signed char\f$ signed? -#define SCHAR_ROUNDS 0x0 -/// \brief Rounding style of type \f$signed char\f$. +/// \brief Rounding style of type \emph{signed char}. +#define SCHAR_ROUNDS 0 +/// \brief Number of radix digits represented by \emph{signed char}. #define SCHAR_RADIX_DIG 0x7 -/// \brief Number of radix digits represented by \f$signed char\f$. +/// \brief Number of decimal digits represented by \emph{signed char}. #define SCHAR_DIG 0x2 -/// \brief Number of decimal digits represented by \f$signed char\f$. -#define SCHAR_DECIMAL_DIG 0x0 -/// \brief Number of decimal digits necessary to differentiate all values of type \f$signed char\f$. +/// \brief Number of decimal digits necessary to differentiate all values of type \emph{signed char}. +#define SCHAR_DECIMAL_DIG 0 +/// \brief The radix, or integer base, used to represent a \emph{signed char}. #define SCHAR_RADIX 0x2 -/// \brief Do arithmetics operations with \f$signed char\f$ trap? -#define SCHAR_TRAPS 0xtrue -/// \brief Smallest finite value of \f$signed char\f$. -#define SCHAR_MIN 0x80 -/// \brief Largest finite value of \f$signed char\f$. +/// \brief Do arithmetics operations with \emph{signed char} trap? +#define SCHAR_TRAPS true +/// \brief Smallest finite value of \emph{signed char}. +#define SCHAR_MIN -0x80 +/// \brief Largest finite value of \emph{signed char}. #define SCHAR_MAX 0x7f -/// \brief Is \f$unsigned char\f$ unsigned? -#define UCHAR_ROUNDS 0x0 -/// \brief Rounding style of type \f$unsigned char\f$. +/// \brief Rounding style of type \emph{unsigned char}. +#define UCHAR_ROUNDS 0 +/// \brief Number of radix digits represented by \emph{unsigned char}. #define UCHAR_RADIX_DIG 0x8 -/// \brief Number of radix digits represented by \f$unsigned char\f$. +/// \brief Number of decimal digits represented by \emph{unsigned char}. #define UCHAR_DIG 0x2 -/// \brief Number of decimal digits represented by \f$unsigned char\f$. -#define UCHAR_DECIMAL_DIG 0x0 -/// \brief Number of decimal digits necessary to differentiate all values of type \f$unsigned char\f$. +/// \brief Number of decimal digits necessary to differentiate all values of type \emph{unsigned char}. +#define UCHAR_DECIMAL_DIG 0 +/// \brief The radix, or integer base, used to represent an \emph{unsigned char}. #define UCHAR_RADIX 0x2 -/// \brief Do arithmetics operations with \f$unsigned char\f$ trap? -#define UCHAR_TRAPS 0xtrue -/// \brief Smallest finite value of \f$unsigned char\f$. +/// \brief Do arithmetics operations with \emph{unsigned char} trap? +#define UCHAR_TRAPS true +/// \brief Smallest finite value of \emph{unsigned char}. #define UCHAR_MIN 0x0 -/// \brief Largest finite value of \f$unsigned char\f$. +/// \brief Largest finite value of \emph{unsigned char}. #define UCHAR_MAX 0xff -/// \brief Rounding style of type \f$short\f$. -#define SHORT_ROUNDS 0x0 -/// \brief Number of radix digits represented by \f$short\f$. +/// \brief Rounding style of type \emph{short}. +#define SHORT_ROUNDS 0 +/// \brief Number of radix digits represented by \emph{short}. #define SHORT_RADIX_DIG 0xf -/// \brief Number of decimal digits represented by \f$short\f$. +/// \brief Number of decimal digits represented by \emph{short}. #define SHORT_DIG 0x4 -/// \brief Number of decimal digits necessary to differentiate all values of type \f$short\f$. -#define SHORT_DECIMAL_DIG 0x0 -/// \brief The radix, or integer base, used to represent a \f$short\f$. +/// \brief Number of decimal digits necessary to differentiate all values of type \emph{short}. +#define SHORT_DECIMAL_DIG 0 +/// \brief The radix, or integer base, used to represent a \emph{short}. #define SHORT_RADIX 0x2 -/// \brief Do arithmetics operations with \f$short\f$ trap? -#define SHORT_TRAPS 0xtrue -/// \brief Smallest finite value of \f$short\f$. -#define SHORT_MIN 0xffff8000 -/// \brief Largest finite value of \f$short\f$. +/// \brief Do arithmetics operations with \emph{short} trap? +#define SHORT_TRAPS true +/// \brief Smallest finite value of \emph{short}. +#define SHORT_MIN 0x8000 +/// \brief Largest finite value of \emph{short}. #define SHORT_MAX 0x7fff -/// \brief Rounding style of type \f$unsigned short\f$. -#define USHORT_ROUNDS 0x0 -/// \brief Number of radix digits represented by \f$unsigned short\f$. +/// \brief Rounding style of type \emph{unsigned short}. +#define USHORT_ROUNDS 0 +/// \brief Number of radix digits represented by \emph{unsigned short}. #define USHORT_RADIX_DIG 0x10 -/// \brief Number of decimal digits represented by \f$unsigned short\f$. +/// \brief Number of decimal digits represented by \emph{unsigned short}. #define USHORT_DIG 0x4 -/// \brief Number of decimal digits necessary to differentiate all values of type \f$unsigned short\f$. -#define USHORT_DECIMAL_DIG 0x0 -/// \brief The radix, or integer base, used to represent a \f$unsigned short\f$. +/// \brief Number of decimal digits necessary to differentiate all values of type \emph{unsigned short}. +#define USHORT_DECIMAL_DIG 0 +/// \brief The radix, or integer base, used to represent an \emph{unsigned short}. #define USHORT_RADIX 0x2 -/// \brief Do arithmetics operations with \f$unsigned short\f$ trap? -#define USHORT_TRAPS 0xtrue -/// \brief Smallest finite value of \f$unsigned short\f$. -#define USHORT_MIN 0x0 -/// \brief Largest finite value of \f$unsigned short\f$. +/// \brief Do arithmetics operations with \emph{unsigned short} trap? +#define USHORT_TRAPS true +/// \brief Smallest finite value of \emph{unsigned short}. +#define USHORT_MIN 0 +/// \brief Largest finite value of \emph{unsigned short}. #define USHORT_MAX 0xffff -/// \brief Rounding style of type \f$int\f$. -#define INT_ROUNDS 0x0 -/// \brief Number of radix digits represented by \f$int\f$. +/// \brief Rounding style of type \emph{int}. +#define INT_ROUNDS 0 +/// \brief Number of radix digits represented by \emph{int}. #define INT_RADIX_DIG 0x1f -/// \brief Number of decimal digits represented by \f$int\f$. +/// \brief Number of decimal digits represented by \emph{int}. #define INT_DIG 0x9 -/// \brief Number of decimal digits necessary to differentiate all values of type \f$int\f$. -#define INT_DECIMAL_DIG 0x0 -/// \brief The radix, or integer base, used to represent a \f$int\f$. +/// \brief Number of decimal digits necessary to differentiate all values of type \emph{int}. +#define INT_DECIMAL_DIG 0 +/// \brief The radix, or integer base, used to represent an \emph{int}. #define INT_RADIX 0x2 -/// \brief Do arithmetics operations with \f$int\f$ trap? -#define INT_TRAPS 0xtrue -/// \brief Smallest finite value of \f$int\f$. +/// \brief Do arithmetics operations with \emph{int} trap? +#define INT_TRAPS true +/// \brief Smallest finite value of \emph{int}. #define INT_MIN 0x80000000 -/// \brief Largest finite value of \f$int\f$. +/// \brief Largest finite value of \emph{int}. #define INT_MAX 0x7fffffff -/// \brief Rounding style of type \f$unsigned int\f$. -#define UINT_ROUNDS 0x0 -/// \brief Number of radix digits represented by \f$unsigned int\f$. +/// \brief Rounding style of type \emph{unsigned int}. +#define UINT_ROUNDS 0 +/// \brief Number of radix digits represented by \emph{unsigned int}. #define UINT_RADIX_DIG 0x20 -/// \brief Number of decimal digits represented by \f$unsigned int\f$. +/// \brief Number of decimal digits represented by \emph{unsigned int}. #define UINT_DIG 0x9 -/// \brief Number of decimal digits necessary to differentiate all values of type \f$unsigned int\f$. -#define UINT_DECIMAL_DIG 0x0 -/// \brief The radix, or unsigned integer base, used to represent a \f$unsigned int\f$. +/// \brief Number of decimal digits necessary to differentiate all values of type \emph{unsigned int}. +#define UINT_DECIMAL_DIG 0 +/// \brief The radix, or integer base, used to represent an \emph{unsigned int}. #define UINT_RADIX 0x2 -/// \brief Do arithmetics operations with \f$unsigned int\f$ trap? -#define UINT_TRAPS 0xtrue -/// \brief Smallest finite value of \f$unsigned int\f$. -#define UINT_MIN 0x0 -/// \brief Largest finite value of \f$unsigned int\f$. +/// \brief Do arithmetics operations with \emph{unsigned int} trap? +#define UINT_TRAPS true +/// \brief Smallest finite value of \emph{unsigned int}. +#define UINT_MIN 0 +/// \brief Largest finite value of \emph{unsigned int}. #define UINT_MAX 0xffffffff -/// \brief Rounding style of type \f$long int\f$. -#define LONG_ROUNDS 0x0 -/// \brief Number of radix digits represented by \f$long int\f$. +/// \brief Rounding style of type \emph{long int}. +#define LONG_ROUNDS 0 +/// \brief Number of radix digits represented by \emph{long int}. #define LONG_RADIX_DIG 0x3f -/// \brief Number of decimal digits represented by \f$long int\f$. +/// \brief Number of decimal digits represented by \emph{long int}. #define LONG_DIG 0x12 -/// \brief Number of decimal digits necessary to differentiate all values of type \f$long int\f$. -#define LONG_DECIMAL_DIG 0x0 -/// \brief The radix, or long integer base, used to represent a \f$long int\f$. +/// \brief Number of decimal digits necessary to differentiate all values of type \emph{long int}. +#define LONG_DECIMAL_DIG 0 +/// \brief The radix, or integer base, used to represent a \emph{long int}. #define LONG_RADIX 0x2 -/// \brief Do arithmetics operations with \f$long int\f$ trap? -#define LONG_TRAPS 0xtrue -/// \brief Smallest finite value of \f$long int\f$. +/// \brief Do arithmetics operations with \emph{long int} trap? +#define LONG_TRAPS true +/// \brief Smallest finite value of \emph{long int}. #define LONG_MIN 0x8000000000000000 -/// \brief Largest finite value of \f$long int\f$. +/// \brief Largest finite value of \emph{long int}. #define LONG_MAX 0x7fffffffffffffff -/// \brief Rounding style of type \f$unsigned long int\f$. -#define ULONG_ROUNDS 0x0 -/// \brief Number of radix digits represented by \f$unsigned long int\f$. +/// \brief Rounding style of type \emph{unsigned long int}. +#define ULONG_ROUNDS 0 +/// \brief Number of radix digits represented by \emph{unsigned long int}. #define ULONG_RADIX_DIG 0x40 -/// \brief Number of decimal digits represented by \f$unsigned long int\f$. +/// \brief Number of decimal digits represented by \emph{unsigned long int}. #define ULONG_DIG 0x13 -/// \brief Number of decimal digits necessary to differentiate all values of type \f$unsigned long int\f$. -#define ULONG_DECIMAL_DIG 0x0 -/// \brief The radix, or unsigned long integer base, used to represent a \f$unsigned long int\f$. +/// \brief Number of decimal digits necessary to differentiate all values of type \emph{unsigned long int}. +#define ULONG_DECIMAL_DIG 0 +/// \brief The radix, or integer base, used to represent an \emph{unsigned long int}. #define ULONG_RADIX 0x2 -/// \brief Do arithmetics operations with \f$unsigned long int\f$ trap? -#define ULONG_TRAPS 0xtrue -/// \brief Smallest finite value of \f$unsigned long int\f$. -#define ULONG_MIN 0x0 -/// \brief Largest finite value of \f$unsigned long int\f$. +/// \brief Do arithmetics operations with \emph{unsigned long int} trap? +#define ULONG_TRAPS true +/// \brief Smallest finite value of \emph{unsigned long int}. +#define ULONG_MIN 0 +/// \brief Largest finite value of \emph{unsigned long int}. #define ULONG_MAX 0xffffffffffffffff -/// \brief Rounding style of type \f$long long\f$. -#define LLONG_ROUNDS 0x0 -/// \brief Number of radix digits represented by \f$long long\f$. +/// \brief Rounding style of type \emph{long long}. +#define LLONG_ROUNDS 0 +/// \brief Number of radix digits represented by \emph{long long}. #define LLONG_RADIX_DIG 0x3f -/// \brief Number of decimal digits represented by \f$long long\f$. +/// \brief Number of decimal digits represented by \emph{long long}. #define LLONG_DIG 0x12 -/// \brief Number of decimal digits necessary to differentiate all values of type \f$long long\f$. -#define LLONG_DECIMAL_DIG 0x0 -/// \brief The radix, or long longeger base, used to represent a \f$long long\f$. +/// \brief Number of decimal digits necessary to differentiate all values of type \emph{long long}. +#define LLONG_DECIMAL_DIG 0 +/// \brief The radix, or integer base, used to represent a \emph{long long}. #define LLONG_RADIX 0x2 -/// \brief Do arithmetics operations with \f$long long\f$ trap? -#define LLONG_TRAPS 0xtrue -/// \brief Smallest finite value of \f$long long\f$. +/// \brief Do arithmetics operations with \emph{long long} trap? +#define LLONG_TRAPS true +/// \brief Smallest finite value of \emph{long long}. #define LLONG_MIN 0x8000000000000000 -/// \brief Largest finite value of \f$long long\f$. +/// \brief Largest finite value of \emph{long long}. #define LLONG_MAX 0x7fffffffffffffff -/// \brief Rounding style of type \f$unsigned long long\f$. -#define ULLONG_ROUNDS 0x0 -/// \brief Number of radix digits represented by \f$unsigned long long\f$. +/// \brief Rounding style of type \emph{unsigned long long}. +#define ULLONG_ROUNDS 0 +/// \brief Number of radix digits represented by \emph{unsigned long long}. #define ULLONG_RADIX_DIG 0x40 -/// \brief Number of decimal digits represented by \f$unsigned long long\f$. +/// \brief Number of decimal digits represented by \emph{unsigned long long}. #define ULLONG_DIG 0x13 -/// \brief Number of decimal digits necessary to differentiate all values of type \f$unsigned long long\f$. -#define ULLONG_DECIMAL_DIG 0x0 -/// \brief The radix, or unsigned long longeger base, used to represent a \f$unsigned long long\f$. +/// \brief Number of decimal digits necessary to differentiate all values of type \emph{unsigned long long}. +#define ULLONG_DECIMAL_DIG 0 +/// \brief The radix, or integer base, used to represent an \emph{unsigned long long}. #define ULLONG_RADIX 0x2 -/// \brief Do arithmetics operations with \f$unsigned long long\f$ trap? -#define ULLONG_TRAPS 0xtrue -/// \brief Smallest finite value of \f$unsigned long long\f$. -#define ULLONG_MIN 0x0 -/// \brief Largest finite value of \f$unsigned long long\f$. +/// \brief Do arithmetics operations with \emph{unsigned long long} trap? +#define ULLONG_TRAPS true +/// \brief Smallest finite value of \emph{unsigned long long}. +#define ULLONG_MIN 0 +/// \brief Largest finite value of \emph{unsigned long long}. #define ULLONG_MAX 0xffffffffffffffff #endif // FENNEC_LANG_INTEGER_H diff --git a/include/fennec/lang/intrinsics.h b/include/fennec/lang/intrinsics.h index a5417e3..8a6b0a2 100644 --- a/include/fennec/lang/intrinsics.h +++ b/include/fennec/lang/intrinsics.h @@ -40,59 +40,59 @@ /// Syntax /// Description ///
-/// \f$FENNEC_HAS_BUILTIN_BIT_CAST\f$
-/// \f$Y FENNEC_BUILTIN_BIT_CAST(X)\f$ +/// \emph{FENNEC_HAS_BUILTIN_BIT_CAST}
+/// \emph{Y FENNEC_BUILTIN_BIT_CAST(X)} /// -/// An intrinsic for doing a bitwise cast without using \f$reinterpret_cast\f$. +/// An intrinsic for doing a bitwise cast without using \emph{reinterpret_cast}. /// ///
-/// \f$FENNEC_HAS_BUILTIN_ADDRESSOF\f$
-/// \f$Y FENNEC_BUILTIN_ADDRESSOF(X)\f$ +/// \emph{FENNEC_HAS_BUILTIN_ADDRESSOF}
+/// \emph{Y FENNEC_BUILTIN_ADDRESSOF(X)} /// -/// Obtains the true address of an object in circumstances where \f$operator&\f$ is overloaded. +/// Obtains the true address of an object in circumstances where \emph{operator&} is overloaded. /// ///
-/// \f$FENNEC_HAS_BUILTIN_IS_CONVERTIBLE\f$
-/// \f$B FENNEC_BUILTIN_IS_CONVERTIBLE(X, Y)\f$ +/// \emph{FENNEC_HAS_BUILTIN_IS_CONVERTIBLE}
+/// \emph{B FENNEC_BUILTIN_IS_CONVERTIBLE(X, Y)} /// -/// Checks if type \f$X\f$ can be converted to type \f$Y\f$. +/// Checks if type \emph{X} can be converted to type \emph{Y}. /// ///
-/// \f$FENNEC_HAS_BUILTIN_IS_EMPTY\f$
-/// \f$B FENNEC_BUILTIN_IS_EMPTY(X)\f$ +/// \emph{FENNEC_HAS_BUILTIN_IS_EMPTY}
+/// \emph{B FENNEC_BUILTIN_IS_EMPTY(X)} /// -/// Checks if type \f$X\f$ stores no data. +/// Checks if type \emph{X} stores no data. /// ///
-/// \f$FENNEC_HAS_BUILTIN_IS_POLYMORPHIC\f$
-/// \f$B FENNEC_BUILTIN_IS_POLYMORPHIC(X)\f$ +/// \emph{FENNEC_HAS_BUILTIN_IS_POLYMORPHIC}
+/// \emph{B FENNEC_BUILTIN_IS_POLYMORPHIC(X)} /// -/// Checks if type \f$X\f$ is polymorphic, this is for classes only thus checks only for subtyping +/// Checks if type \emph{X} is polymorphic, this is for classes only thus checks only for subtyping /// ///
-/// \f$FENNEC_HAS_BUILTIN_IS_FINAL\f$
-/// \f$B FENNEC_BUILTIN_IS_FINAL(X)\f$ +/// \emph{FENNEC_HAS_BUILTIN_IS_FINAL}
+/// \emph{B FENNEC_BUILTIN_IS_FINAL(X)} /// -/// Checks if type \f$X\f$ is final, meaning a function or class cannot be derived from. +/// Checks if type \emph{X} is final, meaning a function or class cannot be derived from. /// ///
-/// \f$FENNEC_HAS_BUILTIN_IS_ABSTRACT\f$
-/// \f$B FENNEC_BUILTIN_IS_ABSTRACT(X)\f$ +/// \emph{FENNEC_HAS_BUILTIN_IS_ABSTRACT}
+/// \emph{B FENNEC_BUILTIN_IS_ABSTRACT(X)} /// -/// Opposite of \f$FENNEC_BUILTIN_IS_FINAL\f$, checks if abstract, meaning \f$X\f$ has at least one pure virtual function. +/// Opposite of \emph{FENNEC_BUILTIN_IS_FINAL}, checks if abstract, meaning \emph{X} has at least one pure virtual function. /// ///
-/// \f$FENNEC_HAS_BUILTIN_IS_STANDARD_LAYOUT\f$
-/// \f$B FENNEC_BUILTIN_IS_STANDARD_LAYOUT(X)\f$ +/// \emph{FENNEC_HAS_BUILTIN_IS_STANDARD_LAYOUT}
+/// \emph{B FENNEC_BUILTIN_IS_STANDARD_LAYOUT(X)} /// -/// Checks if \f$X\f$ has a standard layout, here is [full criteria](https://www.cppreference.com/w/cpp/language/classes.html#Standard-layout_class) +/// Checks if \emph{X} has a standard layout, here is [full criteria](https://www.cppreference.com/w/cpp/language/classes.html#Standard-layout_class) /// for this trait /// ///
-/// \f$FENNEC_HAS_BUILTIN_IS_CONSTRUCTIBLE\f$
-/// \f$B FENNEC_BUILTIN_IS_CONSTRUCTIBLE(X, ...)\f$ +/// \emph{FENNEC_HAS_BUILTIN_IS_CONSTRUCTIBLE}
+/// \emph{B FENNEC_BUILTIN_IS_CONSTRUCTIBLE(X, ...)} /// -/// Checks if type \f$X\f$ is constructible with args \f$\ldots\f$, such that \f$X::X(...)\f$ exists. +/// Checks if type \emph{X} is constructible with args \emph{\ldots}, such that \emph{X::X(...)} exists. /// /// /// @@ -242,8 +242,16 @@ // Difficult and Inconsistent without intrinsics #if __has_builtin(__has_trivial_destructor) +# define FENNEC_HAS_BUILTIN_HAS_TRIVIAL_DESTRUCTOR 1 +# define FENNEC_BUILTIN_HAS_TRIVIAL_DESTRUCTOR(type) __has_trivial_destructor(type) +#else +# define FENNEC_HAS_BUILTIN_HAS_TRIVIAL_DESTRUCTOR 0 +#endif + +// Difficult and Inconsistent without intrinsics +#if __has_builtin(__is_trivially_destructible) # define FENNEC_HAS_BUILTIN_IS_TRIVIALLY_DESTRUCTIBLE 1 -# define FENNEC_BUILTIN_IS_TRIVIALLY_DESTRUCTIBLE(type) __has_trivial_destructor(type) +# define FENNEC_BUILTIN_IS_TRIVIALLY_DESTRUCTIBLE(type) __is_trivially_destructible(type) #else # define FENNEC_HAS_BUILTIN_IS_TRIVIALLY_DESTRUCTIBLE 0 #endif diff --git a/include/fennec/lang/limits.h b/include/fennec/lang/limits.h index 71cf9b6..6d63f29 100644 --- a/include/fennec/lang/limits.h +++ b/include/fennec/lang/limits.h @@ -231,7 +231,7 @@ template struct numeric_limits static constexpr bool has_signaling_nan = false; //!< Check if TypeT can hold a signaling nan static constexpr bool has_denorm = false; //!< Check if TypeT denormalizes static constexpr bool has_denorm_loss = false; //!< Check if TypeT has precision loss when denormalized - static constexpr bool is_iec559 = false; //!< Check if a TypeT representing a float is IEC 559 or IEEE 754 + static constexpr bool is_iec559 = false; //!< Check if TypeT represents an IEC 559 or IEEE 754 static constexpr bool is_bounded = false; //!< Check if TypeT represents a finite set of values static constexpr bool is_modulo = false; //!< Check if TypeT can handle modulo arithmetic static constexpr bool tinyness_before = false; //!< Check if TypeT checks for tinyness before rounding @@ -260,500 +260,515 @@ template struct numeric_limits static constexpr TypeT denorm_min() { return TypeT(); } //!< \returns a value of TypeT holding the smallest positive subnormal }; -// Overload definitions for basic types -// Overload for the builtin floating point type +// Overloads =========================================================================================================== + +/// +/// \brief Definition for type \emph{float}. template<> struct numeric_limits { - static constexpr bool is_specialized = true; - static constexpr bool is_signed = true; - static constexpr bool is_integer = false; - static constexpr bool is_exact = false; - static constexpr bool has_infinity = FLT_HAS_INFINITY; - static constexpr bool has_quiet_nan = FLT_HAS_QUIET_NAN; - static constexpr bool has_signaling_nan = FLT_HAS_SIGNALING_NAN; - static constexpr bool has_denorm = FLT_HAS_DENORM; - static constexpr bool has_denorm_loss = FLT_HAS_DENORM_LOSS; - static constexpr bool is_iec559 = FLT_IS_IEC559; - static constexpr bool is_bounded = true; - static constexpr bool is_modulo = false; - static constexpr bool tinyness_before = FLT_TINYNESS_BEFORE; - static constexpr bool traps = FLT_TRAPS; + static constexpr bool is_specialized = true; //!< Check if the template is specialized for float + static constexpr bool is_signed = true; //!< Check if float is signed + static constexpr bool is_integer = false; //!< Check if float is of an integral type + static constexpr bool is_exact = false; //!< Check if float is exact in its precision + static constexpr bool has_infinity = FLT_HAS_INFINITY; //!< Check if float can hold a value representing infinity + static constexpr bool has_quiet_nan = FLT_HAS_QUIET_NAN; //!< Check if float can hold a non-signaling nan + static constexpr bool has_signaling_nan = FLT_HAS_SIGNALING_NAN; //!< Check if float can hold a signaling nan + static constexpr bool has_denorm = FLT_HAS_DENORM; //!< Check if float denormalizes + static constexpr bool has_denorm_loss = FLT_HAS_DENORM_LOSS; //!< Check if float has precision loss when denormalized + static constexpr bool is_iec559 = FLT_IS_IEC559; //!< Check if float represents an IEC 559 or IEEE 754 + static constexpr bool is_bounded = true; //!< Check if float represents a finite set of values + static constexpr bool is_modulo = false; //!< Check if float can handle modulo arithmetic + static constexpr bool tinyness_before = FLT_TINYNESS_BEFORE; //!< Check if float checks for tinyness before rounding + static constexpr bool traps = FLT_TRAPS; //!< Check if float can cause operations to trap - static constexpr int digits = FLT_MANT_DIG; - static constexpr int digits10 = FLT_DIG; - static constexpr int max_digits10 = FLT_DECIMAL_DIG; - static constexpr int radix = FLT_RADIX; - static constexpr int min_exponent = FLT_MIN_EXP; - static constexpr int min_exponent10 = FLT_MIN_10_EXP; - static constexpr int max_exponent = FLT_MAX_EXP; - static constexpr int max_exponent10 = FLT_MAX_10_EXP; + static constexpr int digits = FLT_MANT_DIG; //!< Get the base representation of the type + static constexpr int digits10 = FLT_DIG; //!< Get the number of radix digits float represents + static constexpr int max_digits10 = FLT_DECIMAL_DIG; //!< Get the number of decimal digits float represents + static constexpr int radix = FLT_RADIX; //!< Get the maximum number of decimal digits float represents + static constexpr int min_exponent = FLT_MIN_EXP; //!< Get the minimum number of radix digits that represent the exponent of float + static constexpr int min_exponent10 = FLT_MIN_10_EXP; //!< Get the minimum number of decimal digits that represent the exponent of float + static constexpr int max_exponent = FLT_MAX_EXP; //!< Get the maximum number of radix digits that represent the exponent of float + static constexpr int max_exponent10 = FLT_MAX_10_EXP; //!< Get the maximum number of decimal digits that represent the exponent of float - static constexpr float min() { return -FLT_MAX; } - static constexpr float max() { return FLT_MAX; } - static constexpr float lowest() { return FLT_MIN; } - static constexpr float epsilon() { return FLT_EPSILON; } - static constexpr float round_error() { return FLT_ROUND_ERR; } - static constexpr float infinity() { return FLT_INF; } - static constexpr float quiet_NaN() { return FLT_QUIET_NAN; } - static constexpr float signaling_NaN() { return FLT_SIGNALING_NAN; } - static constexpr float denorm_min() { return FLT_DENORM_MIN; } + static constexpr float min() { return -FLT_MAX; } //!< \returns the minimum finite value of float + static constexpr float max() { return FLT_MAX; } //!< \returns the maximum finite value of float + static constexpr float lowest() { return FLT_MIN; } //!< \returns the smallest positive value of float + static constexpr float epsilon() { return FLT_EPSILON; } //!< \returns the difference between 1.0 and the next representable value + static constexpr float round_error() { return FLT_ROUND_ERR; } //!< \returns the max rounding error of float + static constexpr float infinity() { return FLT_INF; } //!< \returns a value of float holding a positive infinity + static constexpr float quiet_NaN() { return FLT_QUIET_NAN; } //!< \returns a value of float holding a quiet NaN + static constexpr float signaling_NaN() { return FLT_SIGNALING_NAN; } //!< \returns a value of float holding a signaling NaN + static constexpr float denorm_min() { return FLT_DENORM_MIN; } //!< \returns a value of float holding the smallest positive subnormal }; -// Overload for the bultin double precision floating point type + +/// +/// \brief Definition for type \emph{double}. template<> struct numeric_limits { - static constexpr bool is_specialized = true; - static constexpr bool is_signed = true; - static constexpr bool is_integer = false; - static constexpr bool is_exact = false; - static constexpr bool has_infinity = DBL_HAS_INFINITY; - static constexpr bool has_quiet_nan = DBL_HAS_QUIET_NAN; - static constexpr bool has_signaling_nan = DBL_HAS_SIGNALING_NAN; - static constexpr bool has_denorm = DBL_HAS_DENORM; - static constexpr bool has_denorm_loss = DBL_HAS_DENORM_LOSS; - static constexpr bool is_iec559 = DBL_IS_IEC559; - static constexpr bool is_bounded = true; - static constexpr bool is_modulo = false; - static constexpr bool tinyness_before = DBL_TINYNESS_BEFORE; - static constexpr bool traps = DBL_TRAPS; + static constexpr bool is_specialized = true; //!< Check if the template is specialized for double + static constexpr bool is_signed = true; //!< Check if double is signed + static constexpr bool is_integer = false; //!< Check if double is of an integral type + static constexpr bool is_exact = false; //!< Check if double is exact in its precision + static constexpr bool has_infinity = DBL_HAS_INFINITY; //!< Check if double can hold a value representing infinity + static constexpr bool has_quiet_nan = DBL_HAS_QUIET_NAN; //!< Check if double can hold a non-signaling nan + static constexpr bool has_signaling_nan = DBL_HAS_SIGNALING_NAN; //!< Check if double can hold a signaling nan + static constexpr bool has_denorm = DBL_HAS_DENORM; //!< Check if double denormalizes + static constexpr bool has_denorm_loss = DBL_HAS_DENORM_LOSS; //!< Check if double has precision loss when denormalized + static constexpr bool is_iec559 = DBL_IS_IEC559; //!< Check if double represents an IEC 559 or IEEE 754 + static constexpr bool is_bounded = true; //!< Check if double represents a finite set of values + static constexpr bool is_modulo = false; //!< Check if double can handle modulo arithmetic + static constexpr bool tinyness_before = DBL_TINYNESS_BEFORE; //!< Check if double checks for tinyness before rounding + static constexpr bool traps = DBL_TRAPS; //!< Check if double can cause operations to trap - static constexpr int digits = DBL_MANT_DIG; - static constexpr int digits10 = DBL_DIG; - static constexpr int max_digits10 = DBL_DECIMAL_DIG; - static constexpr int radix = DBL_RADIX; - static constexpr int min_exponent = DBL_MIN_EXP; - static constexpr int min_exponent10 = DBL_MIN_10_EXP; - static constexpr int max_exponent = DBL_MAX_EXP; - static constexpr int max_exponent10 = DBL_MAX_10_EXP; + static constexpr int digits = DBL_MANT_DIG; //!< Get the base representation of the type + static constexpr int digits10 = DBL_DIG; //!< Get the number of radix digits double represents + static constexpr int max_digits10 = DBL_DECIMAL_DIG; //!< Get the number of decimal digits double represents + static constexpr int radix = DBL_RADIX; //!< Get the maximum number of decimal digits double represents + static constexpr int min_exponent = DBL_MIN_EXP; //!< Get the minimum number of radix digits that represent the exponent of double + static constexpr int min_exponent10 = DBL_MIN_10_EXP; //!< Get the minimum number of decimal digits that represent the exponent of double + static constexpr int max_exponent = DBL_MAX_EXP; //!< Get the maximum number of radix digits that represent the exponent of double + static constexpr int max_exponent10 = DBL_MAX_10_EXP; //!< Get the maximum number of decimal digits that represent the exponent of double - static constexpr double min() { return -DBL_MAX; } - static constexpr double max() { return DBL_MAX; } - static constexpr double lowest() { return DBL_MIN; } - static constexpr double epsilon() { return DBL_EPSILON; } - static constexpr double round_error() { return DBL_ROUND_ERR; } - static constexpr double infinity() { return DBL_INF; } - static constexpr double quiet_NaN() { return DBL_QUIET_NAN; } - static constexpr double signaling_NaN() { return DBL_SIGNALING_NAN; } - static constexpr double denorm_min() { return DBL_DENORM_MIN; } + static constexpr double min() { return -DBL_MAX; } //!< \returns the minimum finite value of double + static constexpr double max() { return DBL_MAX; } //!< \returns the maximum finite value of double + static constexpr double lowest() { return DBL_MIN; } //!< \returns the smallest positive value of double + static constexpr double epsilon() { return DBL_EPSILON; } //!< \returns the difference between 1.0 and the next representable value + static constexpr double round_error() { return DBL_ROUND_ERR; } //!< \returns the max rounding error of double + static constexpr double infinity() { return DBL_INF; } //!< \returns a value of double holding a positive infinity + static constexpr double quiet_NaN() { return DBL_QUIET_NAN; } //!< \returns a value of double holding a quiet NaN + static constexpr double signaling_NaN() { return DBL_SIGNALING_NAN; } //!< \returns a value of double holding a signaling NaN + static constexpr double denorm_min() { return DBL_DENORM_MIN; } //!< \returns a value of double holding the smallest positive subnormal }; -// Overload for the builtin char type +/// +/// \brief Definition for type \emph{char}. template<> struct numeric_limits { - static constexpr bool is_specialized = true; - static constexpr bool is_signed = CHAR_IS_SIGNED; - static constexpr bool is_integer = true; - static constexpr bool is_exact = true; - static constexpr bool has_infinity = false; - static constexpr bool has_quiet_nan = false; - static constexpr bool has_signaling_nan = false; - static constexpr bool has_denorm = false; - static constexpr bool has_denorm_loss = false; - static constexpr bool is_iec559 = false; - static constexpr bool is_bounded = true; - static constexpr bool is_modulo = true; - static constexpr bool tinyness_before = false; - static constexpr bool traps = true; + static constexpr bool is_specialized = true; //!< Check if the template is specialized for char + static constexpr bool is_signed = CHAR_IS_SIGNED; //!< Check if char is signed + static constexpr bool is_integer = true; //!< Check if char is of an integral type + static constexpr bool is_exact = true; //!< Check if char is exact in its precision + static constexpr bool has_infinity = false; //!< Check if char can hold a value representing infinity + static constexpr bool has_quiet_nan = false; //!< Check if char can hold a non-signaling nan + static constexpr bool has_signaling_nan = false; //!< Check if char can hold a signaling nan + static constexpr bool has_denorm = false; //!< Check if char denormalizes + static constexpr bool has_denorm_loss = false; //!< Check if char has precision loss when denormalized + static constexpr bool is_iec559 = false; //!< Check if char represents an IEC 559 or IEEE 754 + static constexpr bool is_bounded = true; //!< Check if char represents a finite set of values + static constexpr bool is_modulo = true; //!< Check if char can handle modulo arithmetic + static constexpr bool tinyness_before = false; //!< Check if char checks for tinyness before rounding + static constexpr bool traps = true; //!< Check if char can cause operations to trap - static constexpr int digits = CHAR_RADIX_DIG; - static constexpr int digits10 = CHAR_DIG; - static constexpr int max_digits10 = CHAR_DECIMAL_DIG; - static constexpr int radix = CHAR_RADIX; - static constexpr int min_exponent = 0; - static constexpr int min_exponent10 = 0; - static constexpr int max_exponent = 0; - static constexpr int max_exponent10 = 0; + static constexpr int digits = CHAR_RADIX_DIG; //!< Get the base representation of the type + static constexpr int digits10 = CHAR_DIG; //!< Get the number of radix digits char represents + static constexpr int max_digits10 = CHAR_DECIMAL_DIG; //!< Get the number of decimal digits char represents + static constexpr int radix = CHAR_RADIX; //!< Get the maximum number of decimal digits char represents + static constexpr int min_exponent = 0; //!< Get the minimum number of radix digits that represent the exponent of char + static constexpr int min_exponent10 = 0; //!< Get the minimum number of decimal digits that represent the exponent of char + static constexpr int max_exponent = 0; //!< Get the maximum number of radix digits that represent the exponent of char + static constexpr int max_exponent10 = 0; //!< Get the maximum number of decimal digits that represent the exponent of char - static constexpr char min() { return static_cast(CHAR_MIN); } - static constexpr char max() { return CHAR_MAX; } - static constexpr char lowest() { return 1; } - static constexpr char epsilon() { return 1; } - static constexpr char round_error() { return 0; } - static constexpr char infinity() { return 0; } - static constexpr char quiet_NaN() { return 0; } - static constexpr char signaling_NaN() { return 0; } - static constexpr char denorm_min() { return 0; } + static constexpr char min() { return CHAR_MIN; } //!< \returns the minimum finite value of char + static constexpr char max() { return CHAR_MAX; } //!< \returns the maximum finite value of char + static constexpr char lowest() { return 1; } //!< \returns the smallest positive value of char + static constexpr char epsilon() { return 1; } //!< \returns the difference between 1.0 and the next representable value + static constexpr char round_error() { return 0; } //!< \returns the max rounding error of char + static constexpr char infinity() { return 0; } //!< \returns a value of char holding a positive infinity + static constexpr char quiet_NaN() { return 0; } //!< \returns a value of char holding a quiet NaN + static constexpr char signaling_NaN() { return 0; } //!< \returns a value of char holding a signaling NaN + static constexpr char denorm_min() { return 0; } //!< \returns a value of char holding the smallest positive subnormal }; -// Overload for the builtin signed char type +/// +/// \brief Definition for type \emph{signed char}. template<> struct numeric_limits { - static constexpr bool is_specialized = true; - static constexpr bool is_signed = true; - static constexpr bool is_integer = true; - static constexpr bool is_exact = true; - static constexpr bool has_infinity = false; - static constexpr bool has_quiet_nan = false; - static constexpr bool has_signaling_nan = false; - static constexpr bool has_denorm = false; - static constexpr bool has_denorm_loss = false; - static constexpr bool is_iec559 = false; - static constexpr bool is_bounded = true; - static constexpr bool is_modulo = true; - static constexpr bool tinyness_before = false; - static constexpr bool traps = true; + static constexpr bool is_specialized = true; //!< Check if the template is specialized for signed char + static constexpr bool is_signed = true; //!< Check if signed char is signed + static constexpr bool is_integer = true; //!< Check if signed char is of an integral type + static constexpr bool is_exact = true; //!< Check if signed char is exact in its precision + static constexpr bool has_infinity = false; //!< Check if signed char can hold a value representing infinity + static constexpr bool has_quiet_nan = false; //!< Check if signed char can hold a non-signaling nan + static constexpr bool has_signaling_nan = false; //!< Check if signed char can hold a signaling nan + static constexpr bool has_denorm = false; //!< Check if signed char denormalizes + static constexpr bool has_denorm_loss = false; //!< Check if signed char has precision loss when denormalized + static constexpr bool is_iec559 = false; //!< Check if signed char represents an IEC 559 or IEEE 754 + static constexpr bool is_bounded = true; //!< Check if signed char represents a finite set of values + static constexpr bool is_modulo = true; //!< Check if signed char can handle modulo arithmetic + static constexpr bool tinyness_before = false; //!< Check if signed char checks for tinyness before rounding + static constexpr bool traps = true; //!< Check if signed char can cause operations to trap - static constexpr int digits = SCHAR_RADIX_DIG; - static constexpr int digits10 = SCHAR_DIG; - static constexpr int max_digits10 = SCHAR_DECIMAL_DIG; - static constexpr int radix = SCHAR_RADIX; - static constexpr int min_exponent = 0; - static constexpr int min_exponent10 = 0; - static constexpr int max_exponent = 0; - static constexpr int max_exponent10 = 0; + static constexpr int digits = SCHAR_RADIX_DIG; //!< Get the base representation of the type + static constexpr int digits10 = SCHAR_DIG; //!< Get the number of radix digits signed char represents + static constexpr int max_digits10 = SCHAR_DECIMAL_DIG; //!< Get the number of decimal digits signed char represents + static constexpr int radix = SCHAR_RADIX; //!< Get the maximum number of decimal digits signed char represents + static constexpr int min_exponent = 0; //!< Get the minimum number of radix digits that represent the exponent of signed char + static constexpr int min_exponent10 = 0; //!< Get the minimum number of decimal digits that represent the exponent of signed char + static constexpr int max_exponent = 0; //!< Get the maximum number of radix digits that represent the exponent of signed char + static constexpr int max_exponent10 = 0; //!< Get the maximum number of decimal digits that represent the exponent of signed char - static constexpr signed char min() { return static_cast(SCHAR_MIN); } - static constexpr signed char max() { return SCHAR_MAX; } - static constexpr signed char lowest() { return 1; } - static constexpr signed char epsilon() { return 1; } - static constexpr signed char round_error() { return 0; } - static constexpr signed char infinity() { return 0; } - static constexpr signed char quiet_NaN() { return 0; } - static constexpr signed char signaling_NaN() { return 0; } - static constexpr signed char denorm_min() { return 0; } + static constexpr signed char min() { return SCHAR_MIN; } //!< \returns the minimum finite value of signed char + static constexpr signed char max() { return SCHAR_MAX; } //!< \returns the maximum finite value of signed char + static constexpr signed char lowest() { return 1; } //!< \returns the smallest positive value of signed char + static constexpr signed char epsilon() { return 1; } //!< \returns the difference between 1.0 and the next representable value + static constexpr signed char round_error() { return 0; } //!< \returns the max rounding error of signed char + static constexpr signed char infinity() { return 0; } //!< \returns a value of signed char holding a positive infinity + static constexpr signed char quiet_NaN() { return 0; } //!< \returns a value of signed char holding a quiet NaN + static constexpr signed char signaling_NaN() { return 0; } //!< \returns a value of signed char holding a signaling NaN + static constexpr signed char denorm_min() { return 0; } //!< \returns a value of signed char holding the smallest positive subnormal }; -// Overload for the builtin signed char type +/// +/// \brief Definition for type \emph{unsigned char}. template<> struct numeric_limits { - static constexpr bool is_specialized = true; - static constexpr bool is_signed = false; - static constexpr bool is_integer = true; - static constexpr bool is_exact = true; - static constexpr bool has_infinity = false; - static constexpr bool has_quiet_nan = false; - static constexpr bool has_signaling_nan = false; - static constexpr bool has_denorm = false; - static constexpr bool has_denorm_loss = false; - static constexpr bool is_iec559 = false; - static constexpr bool is_bounded = true; - static constexpr bool is_modulo = true; - static constexpr bool tinyness_before = false; - static constexpr bool traps = true; + static constexpr bool is_specialized = true; //!< Check if the template is specialized for unsigned char + static constexpr bool is_signed = false; //!< Check if unsigned char is unsigned + static constexpr bool is_integer = true; //!< Check if unsigned char is of an integral type + static constexpr bool is_exact = true; //!< Check if unsigned char is exact in its precision + static constexpr bool has_infinity = false; //!< Check if unsigned char can hold a value representing infinity + static constexpr bool has_quiet_nan = false; //!< Check if unsigned char can hold a non-signaling nan + static constexpr bool has_signaling_nan = false; //!< Check if unsigned char can hold a signaling nan + static constexpr bool has_denorm = false; //!< Check if unsigned char denormalizes + static constexpr bool has_denorm_loss = false; //!< Check if unsigned char has precision loss when denormalized + static constexpr bool is_iec559 = false; //!< Check if unsigned char represents an IEC 559 or IEEE 754 + static constexpr bool is_bounded = true; //!< Check if unsigned char represents a finite set of values + static constexpr bool is_modulo = true; //!< Check if unsigned char can handle modulo arithmetic + static constexpr bool tinyness_before = false; //!< Check if unsigned char checks for tinyness before rounding + static constexpr bool traps = true; //!< Check if unsigned char can cause operations to trap - static constexpr int digits = UCHAR_RADIX_DIG; - static constexpr int digits10 = UCHAR_DIG; - static constexpr int max_digits10 = UCHAR_DECIMAL_DIG; - static constexpr int radix = UCHAR_RADIX; - static constexpr int min_exponent = 0; - static constexpr int min_exponent10 = 0; - static constexpr int max_exponent = 0; - static constexpr int max_exponent10 = 0; + static constexpr int digits = UCHAR_RADIX_DIG; //!< Get the base representation of the type + static constexpr int digits10 = UCHAR_DIG; //!< Get the number of radix digits unsigned char represents + static constexpr int max_digits10 = UCHAR_DECIMAL_DIG; //!< Get the number of decimal digits unsigned char represents + static constexpr int radix = UCHAR_RADIX; //!< Get the maximum number of decimal digits unsigned char represents + static constexpr int min_exponent = 0; //!< Get the minimum number of radix digits that represent the exponent of unsigned char + static constexpr int min_exponent10 = 0; //!< Get the minimum number of decimal digits that represent the exponent of unsigned char + static constexpr int max_exponent = 0; //!< Get the maximum number of radix digits that represent the exponent of unsigned char + static constexpr int max_exponent10 = 0; //!< Get the maximum number of decimal digits that represent the exponent of unsigned char - static constexpr unsigned char min() { return UCHAR_MIN; } - static constexpr unsigned char max() { return UCHAR_MAX; } - static constexpr unsigned char lowest() { return 1; } - static constexpr unsigned char epsilon() { return 1; } - static constexpr unsigned char round_error() { return 0; } - static constexpr unsigned char infinity() { return 0; } - static constexpr unsigned char quiet_NaN() { return 0; } - static constexpr unsigned char signaling_NaN() { return 0; } - static constexpr unsigned char denorm_min() { return 0; } + static constexpr unsigned char min() { return UCHAR_MIN; } //!< \returns the minimum finite value of unsigned char + static constexpr unsigned char max() { return UCHAR_MAX; } //!< \returns the maximum finite value of unsigned char + static constexpr unsigned char lowest() { return 1; } //!< \returns the smallest positive value of unsigned char + static constexpr unsigned char epsilon() { return 1; } //!< \returns the difference between 1.0 and the next representable value + static constexpr unsigned char round_error() { return 0; } //!< \returns the max rounding error of unsigned char + static constexpr unsigned char infinity() { return 0; } //!< \returns a value of unsigned char holding a positive infinity + static constexpr unsigned char quiet_NaN() { return 0; } //!< \returns a value of unsigned char holding a quiet NaN + static constexpr unsigned char signaling_NaN() { return 0; } //!< \returns a value of unsigned char holding a signaling NaN + static constexpr unsigned char denorm_min() { return 0; } //!< \returns a value of unsigned char holding the smallest positive subnormal }; -// Overload for the builtin signed char type +/// +/// \brief Definition for type \emph{short}. template<> struct numeric_limits { - static constexpr bool is_specialized = true; - static constexpr bool is_signed = true; - static constexpr bool is_integer = true; - static constexpr bool is_exact = true; - static constexpr bool has_infinity = false; - static constexpr bool has_quiet_nan = false; - static constexpr bool has_signaling_nan = false; - static constexpr bool has_denorm = false; - static constexpr bool has_denorm_loss = false; - static constexpr bool is_iec559 = false; - static constexpr bool is_bounded = true; - static constexpr bool is_modulo = true; - static constexpr bool tinyness_before = false; - static constexpr bool traps = true; + static constexpr bool is_specialized = true; //!< Check if the template is specialized for short + static constexpr bool is_signed = true; //!< Check if short is signed + static constexpr bool is_integer = true; //!< Check if short is of an integral type + static constexpr bool is_exact = true; //!< Check if short is exact in its precision + static constexpr bool has_infinity = false; //!< Check if short can hold a value representing infinity + static constexpr bool has_quiet_nan = false; //!< Check if short can hold a non-signaling nan + static constexpr bool has_signaling_nan = false; //!< Check if short can hold a signaling nan + static constexpr bool has_denorm = false; //!< Check if short denormalizes + static constexpr bool has_denorm_loss = false; //!< Check if short has precision loss when denormalized + static constexpr bool is_iec559 = false; //!< Check if short represents an IEC 559 or IEEE 754 + static constexpr bool is_bounded = true; //!< Check if short represents a finite set of values + static constexpr bool is_modulo = true; //!< Check if short can handle modulo arithmetic + static constexpr bool tinyness_before = false; //!< Check if short checks for tinyness before rounding + static constexpr bool traps = true; //!< Check if short can cause operations to trap - static constexpr int digits = SHORT_RADIX_DIG; - static constexpr int digits10 = SHORT_DIG; - static constexpr int max_digits10 = SHORT_DECIMAL_DIG; - static constexpr int radix = SHORT_RADIX; - static constexpr int min_exponent = 0; - static constexpr int min_exponent10 = 0; - static constexpr int max_exponent = 0; - static constexpr int max_exponent10 = 0; + static constexpr int digits = SHORT_RADIX_DIG; //!< Get the base representation of the type + static constexpr int digits10 = SHORT_DIG; //!< Get the number of radix digits short represents + static constexpr int max_digits10 = SHORT_DECIMAL_DIG; //!< Get the number of decimal digits short represents + static constexpr int radix = SHORT_RADIX; //!< Get the maximum number of decimal digits short represents + static constexpr int min_exponent = 0; //!< Get the minimum number of radix digits that represent the exponent of short + static constexpr int min_exponent10 = 0; //!< Get the minimum number of decimal digits that represent the exponent of short + static constexpr int max_exponent = 0; //!< Get the maximum number of radix digits that represent the exponent of short + static constexpr int max_exponent10 = 0; //!< Get the maximum number of decimal digits that represent the exponent of short - static constexpr short min() { return static_cast(SHORT_MIN); } - static constexpr short max() { return SHORT_MAX; } - static constexpr short lowest() { return 1; } - static constexpr short epsilon() { return 1; } - static constexpr short round_error() { return 0; } - static constexpr short infinity() { return 0; } - static constexpr short quiet_NaN() { return 0; } - static constexpr short signaling_NaN() { return 0; } - static constexpr short denorm_min() { return 0; } + static constexpr short min() { return static_cast(SHORT_MIN); } //!< \returns the minimum finite value of short + static constexpr short max() { return SHORT_MAX; } //!< \returns the maximum finite value of short + static constexpr short lowest() { return 1; } //!< \returns the smallest positive value of short + static constexpr short epsilon() { return 1; } //!< \returns the difference between 1.0 and the next representable value + static constexpr short round_error() { return 0; } //!< \returns the max rounding error of short + static constexpr short infinity() { return 0; } //!< \returns a value of short holding a positive infinity + static constexpr short quiet_NaN() { return 0; } //!< \returns a value of short holding a quiet NaN + static constexpr short signaling_NaN() { return 0; } //!< \returns a value of short holding a signaling NaN + static constexpr short denorm_min() { return 0; } //!< \returns a value of short holding the smallest positive subnormal }; -// Overload for the builtin signed char type +/// +/// \brief Definition for type \emph{unsigned short}. template<> struct numeric_limits { - static constexpr bool is_specialized = true; - static constexpr bool is_signed = false; - static constexpr bool is_integer = true; - static constexpr bool is_exact = true; - static constexpr bool has_infinity = false; - static constexpr bool has_quiet_nan = false; - static constexpr bool has_signaling_nan = false; - static constexpr bool has_denorm = false; - static constexpr bool has_denorm_loss = false; - static constexpr bool is_iec559 = false; - static constexpr bool is_bounded = true; - static constexpr bool is_modulo = true; - static constexpr bool tinyness_before = false; - static constexpr bool traps = true; + static constexpr bool is_specialized = true; //!< Check if the template is specialized for signed short + static constexpr bool is_signed = false; //!< Check if unsigned short is signed + static constexpr bool is_integer = true; //!< Check if unsigned short is of an integral type + static constexpr bool is_exact = true; //!< Check if unsigned short is exact in its precision + static constexpr bool has_infinity = false; //!< Check if unsigned short can hold a value representing infinity + static constexpr bool has_quiet_nan = false; //!< Check if unsigned short can hold a non-signaling nan + static constexpr bool has_signaling_nan = false; //!< Check if unsigned short can hold a signaling nan + static constexpr bool has_denorm = false; //!< Check if unsigned short denormalizes + static constexpr bool has_denorm_loss = false; //!< Check if unsigned short has precision loss when denormalized + static constexpr bool is_iec559 = false; //!< Check if unsigned short represents an IEC 559 or IEEE 754 + static constexpr bool is_bounded = true; //!< Check if unsigned short represents a finite set of values + static constexpr bool is_modulo = true; //!< Check if unsigned short can handle modulo arithmetic + static constexpr bool tinyness_before = false; //!< Check if unsigned short checks for tinyness before rounding + static constexpr bool traps = true; //!< Check if unsigned short can cause operations to trap - static constexpr int digits = USHORT_RADIX_DIG; - static constexpr int digits10 = USHORT_DIG; - static constexpr int max_digits10 = USHORT_DECIMAL_DIG; - static constexpr int radix = USHORT_RADIX; - static constexpr int min_exponent = 0; - static constexpr int min_exponent10 = 0; - static constexpr int max_exponent = 0; - static constexpr int max_exponent10 = 0; + static constexpr int digits = USHORT_RADIX_DIG; //!< Get the base representation of the type + static constexpr int digits10 = USHORT_DIG; //!< Get the number of radix digits unsigned short represents + static constexpr int max_digits10 = USHORT_DECIMAL_DIG; //!< Get the number of decimal digits unsigned short represents + static constexpr int radix = USHORT_RADIX; //!< Get the maximum number of decimal digits unsigned short represents + static constexpr int min_exponent = 0; //!< Get the minimum number of radix digits that represent the exponent of unsigned short + static constexpr int min_exponent10 = 0; //!< Get the minimum number of decimal digits that represent the exponent of unsigned short + static constexpr int max_exponent = 0; //!< Get the maximum number of radix digits that represent the exponent of unsigned short + static constexpr int max_exponent10 = 0; //!< Get the maximum number of decimal digits that represent the exponent of unsigned short - static constexpr unsigned short min() { return USHORT_MIN; } - static constexpr unsigned short max() { return USHORT_MAX; } - static constexpr unsigned short lowest() { return 1; } - static constexpr unsigned short epsilon() { return 1; } - static constexpr unsigned short round_error() { return 0; } - static constexpr unsigned short infinity() { return 0; } - static constexpr unsigned short quiet_NaN() { return 0; } - static constexpr unsigned short signaling_NaN() { return 0; } - static constexpr unsigned short denorm_min() { return 0; } + static constexpr unsigned short min() { return USHORT_MIN; } //!< \returns the minimum finite value of unsigned short + static constexpr unsigned short max() { return USHORT_MAX; } //!< \returns the maximum finite value of unsigned short + static constexpr unsigned short lowest() { return 1; } //!< \returns the smallest positive value of unsigned short + static constexpr unsigned short epsilon() { return 1; } //!< \returns the difference between 1.0 and the next representable value + static constexpr unsigned short round_error() { return 0; } //!< \returns the max rounding error of unsigned short + static constexpr unsigned short infinity() { return 0; } //!< \returns a value of unsigned short holding a positive infinity + static constexpr unsigned short quiet_NaN() { return 0; } //!< \returns a value of unsigned short holding a quiet NaN + static constexpr unsigned short signaling_NaN() { return 0; } //!< \returns a value of unsigned short holding a signaling NaN + static constexpr unsigned short denorm_min() { return 0; } //!< \returns a value of unsigned short holding the smallest positive subnormal }; -// Overload for the builtin signed char type +/// +/// \brief Definition for type \emph{int}. template<> struct numeric_limits { - static constexpr bool is_specialized = true; - static constexpr bool is_signed = true; - static constexpr bool is_integer = true; - static constexpr bool is_exact = true; - static constexpr bool has_infinity = false; - static constexpr bool has_quiet_nan = false; - static constexpr bool has_signaling_nan = false; - static constexpr bool has_denorm = false; - static constexpr bool has_denorm_loss = false; - static constexpr bool is_iec559 = false; - static constexpr bool is_bounded = true; - static constexpr bool is_modulo = true; - static constexpr bool tinyness_before = false; - static constexpr bool traps = true; + static constexpr bool is_specialized = true; //!< Check if the template is specialized for int + static constexpr bool is_signed = true; //!< Check if int is signed + static constexpr bool is_integer = true; //!< Check if int is of an integral type + static constexpr bool is_exact = true; //!< Check if int is exact in its precision + static constexpr bool has_infinity = false; //!< Check if int can hold a value representing infinity + static constexpr bool has_quiet_nan = false; //!< Check if int can hold a non-signaling nan + static constexpr bool has_signaling_nan = false; //!< Check if int can hold a signaling nan + static constexpr bool has_denorm = false; //!< Check if int denormalizes + static constexpr bool has_denorm_loss = false; //!< Check if int has precision loss when denormalized + static constexpr bool is_iec559 = false; //!< Check if int represents an IEC 559 or IEEE 754 + static constexpr bool is_bounded = true; //!< Check if int represents a finite set of values + static constexpr bool is_modulo = true; //!< Check if int can handle modulo arithmetic + static constexpr bool tinyness_before = false; //!< Check if int checks for tinyness before rounding + static constexpr bool traps = true; //!< Check if int can cause operations to trap - static constexpr int digits = INT_RADIX_DIG; - static constexpr int digits10 = INT_DIG; - static constexpr int max_digits10 = INT_DECIMAL_DIG; - static constexpr int radix = INT_RADIX; - static constexpr int min_exponent = 0; - static constexpr int min_exponent10 = 0; - static constexpr int max_exponent = 0; - static constexpr int max_exponent10 = 0; + static constexpr int digits = INT_RADIX_DIG; //!< Get the base representation of the type + static constexpr int digits10 = INT_DIG; //!< Get the number of radix digits int represents + static constexpr int max_digits10 = INT_DECIMAL_DIG; //!< Get the number of decimal digits int represents + static constexpr int radix = INT_RADIX; //!< Get the maximum number of decimal digits int represents + static constexpr int min_exponent = 0; //!< Get the minimum number of radix digits that represent the exponent of int + static constexpr int min_exponent10 = 0; //!< Get the minimum number of decimal digits that represent the exponent of int + static constexpr int max_exponent = 0; //!< Get the maximum number of radix digits that represent the exponent of int + static constexpr int max_exponent10 = 0; //!< Get the maximum number of decimal digits that represent the exponent of int - static constexpr int min() { return INT_MIN; } - static constexpr int max() { return INT_MAX; } - static constexpr int lowest() { return 1; } - static constexpr int epsilon() { return 1; } - static constexpr int round_error() { return 0; } - static constexpr int infinity() { return 0; } - static constexpr int quiet_NaN() { return 0; } - static constexpr int signaling_NaN() { return 0; } - static constexpr int denorm_min() { return 0; } + static constexpr int min() { return INT_MIN; } //!< \returns the minimum finite value of int + static constexpr int max() { return INT_MAX; } //!< \returns the maximum finite value of int + static constexpr int lowest() { return 1; } //!< \returns the smallest positive value of int + static constexpr int epsilon() { return 1; } //!< \returns the difference between 1.0 and the next representable value + static constexpr int round_error() { return 0; } //!< \returns the max rounding error of int + static constexpr int infinity() { return 0; } //!< \returns a value of int holding a positive infinity + static constexpr int quiet_NaN() { return 0; } //!< \returns a value of int holding a quiet NaN + static constexpr int signaling_NaN() { return 0; } //!< \returns a value of int holding a signaling NaN + static constexpr int denorm_min() { return 0; } //!< \returns a value of int holding the smallest positive subnormal }; -// Overload for the builtin signed char type +/// +/// \brief Definition for type \emph{unsigned int}. template<> struct numeric_limits { - static constexpr bool is_specialized = true; - static constexpr bool is_signed = false; - static constexpr bool is_integer = true; - static constexpr bool is_exact = true; - static constexpr bool has_infinity = false; - static constexpr bool has_quiet_nan = false; - static constexpr bool has_signaling_nan = false; - static constexpr bool has_denorm = false; - static constexpr bool has_denorm_loss = false; - static constexpr bool is_iec559 = false; - static constexpr bool is_bounded = true; - static constexpr bool is_modulo = true; - static constexpr bool tinyness_before = false; - static constexpr bool traps = true; + static constexpr bool is_specialized = true; //!< Check if the template is specialized for unsigned int + static constexpr bool is_signed = false; //!< Check if unsigned int is signed + static constexpr bool is_integer = true; //!< Check if unsigned int is of an integral type + static constexpr bool is_exact = true; //!< Check if unsigned int is exact in its precision + static constexpr bool has_infinity = false; //!< Check if unsigned int can hold a value representing infinity + static constexpr bool has_quiet_nan = false; //!< Check if unsigned int can hold a non-signaling nan + static constexpr bool has_signaling_nan = false; //!< Check if unsigned int can hold a signaling nan + static constexpr bool has_denorm = false; //!< Check if unsigned int denormalizes + static constexpr bool has_denorm_loss = false; //!< Check if unsigned int has precision loss when denormalized + static constexpr bool is_iec559 = false; //!< Check if unsigned int represents an IEC 559 or IEEE 754 + static constexpr bool is_bounded = true; //!< Check if unsigned int represents a finite set of values + static constexpr bool is_modulo = true; //!< Check if unsigned int can handle modulo arithmetic + static constexpr bool tinyness_before = false; //!< Check if unsigned int checks for tinyness before rounding + static constexpr bool traps = true; //!< Check if unsigned int can cause operations to trap - static constexpr int digits = UINT_RADIX_DIG; - static constexpr int digits10 = UINT_DIG; - static constexpr int max_digits10 = UINT_DECIMAL_DIG; - static constexpr int radix = UINT_RADIX; - static constexpr int min_exponent = 0; - static constexpr int min_exponent10 = 0; - static constexpr int max_exponent = 0; - static constexpr int max_exponent10 = 0; + static constexpr int digits = UINT_RADIX_DIG; //!< Get the base representation of the type + static constexpr int digits10 = UINT_DIG; //!< Get the number of radix digits unsigned int represents + static constexpr int max_digits10 = UINT_DECIMAL_DIG; //!< Get the number of decimal digits unsigned int represents + static constexpr int radix = UINT_RADIX; //!< Get the maximum number of decimal digits unsigned int represents + static constexpr int min_exponent = 0; //!< Get the minimum number of radix digits that represent the exponent of unsigned int + static constexpr int min_exponent10 = 0; //!< Get the minimum number of decimal digits that represent the exponent of unsigned int + static constexpr int max_exponent = 0; //!< Get the maximum number of radix digits that represent the exponent of unsigned int + static constexpr int max_exponent10 = 0; //!< Get the maximum number of decimal digits that represent the exponent of unsigned int - static constexpr unsigned int min() { return UINT_MIN; } - static constexpr unsigned int max() { return UINT_MAX; } - static constexpr unsigned int lowest() { return 1; } - static constexpr unsigned int epsilon() { return 1; } - static constexpr unsigned int round_error() { return 0; } - static constexpr unsigned int infinity() { return 0; } - static constexpr unsigned int quiet_NaN() { return 0; } - static constexpr unsigned int signaling_NaN() { return 0; } - static constexpr unsigned int denorm_min() { return 0; } + static constexpr unsigned int min() { return UINT_MIN; } //!< \returns the minimum finite value of unsigned int + static constexpr unsigned int max() { return UINT_MAX; } //!< \returns the maximum finite value of unsigned int + static constexpr unsigned int lowest() { return 1; } //!< \returns the smallest positive value of unsigned int + static constexpr unsigned int epsilon() { return 1; } //!< \returns the difference between 1.0 and the next representable value + static constexpr unsigned int round_error() { return 0; } //!< \returns the max rounding error of unsigned int + static constexpr unsigned int infinity() { return 0; } //!< \returns a value of unsigned int holding a positive infinity + static constexpr unsigned int quiet_NaN() { return 0; } //!< \returns a value of unsigned int holding a quiet NaN + static constexpr unsigned int signaling_NaN() { return 0; } //!< \returns a value of unsigned int holding a signaling NaN + static constexpr unsigned int denorm_min() { return 0; } //!< \returns a value of unsigned int holding the smallest positive subnormal }; -// Overload for the builtin signed char type +/// +/// \brief Definition for type \emph{long int}. template<> struct numeric_limits { - static constexpr bool is_specialized = true; - static constexpr bool is_signed = true; - static constexpr bool is_integer = true; - static constexpr bool is_exact = true; - static constexpr bool has_infinity = false; - static constexpr bool has_quiet_nan = false; - static constexpr bool has_signaling_nan = false; - static constexpr bool has_denorm = false; - static constexpr bool has_denorm_loss = false; - static constexpr bool is_iec559 = false; - static constexpr bool is_bounded = true; - static constexpr bool is_modulo = true; - static constexpr bool tinyness_before = false; - static constexpr bool traps = true; + static constexpr bool is_specialized = true; //!< Check if the template is specialized for long int + static constexpr bool is_signed = true; //!< Check if long int is signed + static constexpr bool is_integer = true; //!< Check if long int is of an integral type + static constexpr bool is_exact = true; //!< Check if long int is exact in its precision + static constexpr bool has_infinity = false; //!< Check if long int can hold a value representing infinity + static constexpr bool has_quiet_nan = false; //!< Check if long int can hold a non-signaling nan + static constexpr bool has_signaling_nan = false; //!< Check if long int can hold a signaling nan + static constexpr bool has_denorm = false; //!< Check if long int denormalizes + static constexpr bool has_denorm_loss = false; //!< Check if long int has precision loss when denormalized + static constexpr bool is_iec559 = false; //!< Check if long int represents an IEC 559 or IEEE 754 + static constexpr bool is_bounded = true; //!< Check if long int represents a finite set of values + static constexpr bool is_modulo = true; //!< Check if long int can handle modulo arithmetic + static constexpr bool tinyness_before = false; //!< Check if long int checks for tinyness before rounding + static constexpr bool traps = true; //!< Check if long int can cause operations to trap - static constexpr int digits = LONG_RADIX_DIG; - static constexpr int digits10 = LONG_DIG; - static constexpr int max_digits10 = LONG_DECIMAL_DIG; - static constexpr int radix = LONG_RADIX; - static constexpr int min_exponent = 0; - static constexpr int min_exponent10 = 0; - static constexpr int max_exponent = 0; - static constexpr int max_exponent10 = 0; + static constexpr int digits = LONG_RADIX_DIG; //!< Get the base representation of the type + static constexpr int digits10 = LONG_DIG; //!< Get the number of radix digits long int represents + static constexpr int max_digits10 = LONG_DECIMAL_DIG; //!< Get the number of decimal digits long int represents + static constexpr int radix = LONG_RADIX; //!< Get the maximum number of decimal digits long int represents + static constexpr int min_exponent = 0; //!< Get the minimum number of radix digits that represent the exponent of long int + static constexpr int min_exponent10 = 0; //!< Get the minimum number of decimal digits that represent the exponent of long int + static constexpr int max_exponent = 0; //!< Get the maximum number of radix digits that represent the exponent of long int + static constexpr int max_exponent10 = 0; //!< Get the maximum number of decimal digits that represent the exponent of long int - static constexpr long int min() { return LONG_MIN; } - static constexpr long int max() { return LONG_MAX; } - static constexpr long int lowest() { return 1; } - static constexpr long int epsilon() { return 1; } - static constexpr long int round_error() { return 0; } - static constexpr long int infinity() { return 0; } - static constexpr long int quiet_NaN() { return 0; } - static constexpr long int signaling_NaN() { return 0; } - static constexpr long int denorm_min() { return 0; } + static constexpr long int min() { return LONG_MIN; } //!< \returns the minimum finite value of long int + static constexpr long int max() { return LONG_MAX; } //!< \returns the maximum finite value of long int + static constexpr long int lowest() { return 1; } //!< \returns the smallest positive value of long int + static constexpr long int epsilon() { return 1; } //!< \returns the difference between 1.0 and the next representable value + static constexpr long int round_error() { return 0; } //!< \returns the max rounding error of long int + static constexpr long int infinity() { return 0; } //!< \returns a value of long int holding a positive infinity + static constexpr long int quiet_NaN() { return 0; } //!< \returns a value of long int holding a quiet NaN + static constexpr long int signaling_NaN() { return 0; } //!< \returns a value of long int holding a signaling NaN + static constexpr long int denorm_min() { return 0; } //!< \returns a value of long int holding the smallest positive subnormal }; -// Overload for the builtin signed char type +/// +/// \brief Definition for type \emph{unsigned long int}. template<> struct numeric_limits { - static constexpr bool is_specialized = true; - static constexpr bool is_signed = false; - static constexpr bool is_integer = true; - static constexpr bool is_exact = true; - static constexpr bool has_infinity = false; - static constexpr bool has_quiet_nan = false; - static constexpr bool has_signaling_nan = false; - static constexpr bool has_denorm = false; - static constexpr bool has_denorm_loss = false; - static constexpr bool is_iec559 = false; - static constexpr bool is_bounded = true; - static constexpr bool is_modulo = true; - static constexpr bool tinyness_before = false; - static constexpr bool traps = true; + static constexpr bool is_specialized = true; //!< Check if the template is specialized for unsigned long int + static constexpr bool is_signed = false; //!< Check if unsigned long int is signed + static constexpr bool is_integer = true; //!< Check if unsigned long int is of an integral type + static constexpr bool is_exact = true; //!< Check if unsigned long int is exact in its precision + static constexpr bool has_infinity = false; //!< Check if unsigned long int can hold a value representing infinity + static constexpr bool has_quiet_nan = false; //!< Check if unsigned long int can hold a non-signaling nan + static constexpr bool has_signaling_nan = false; //!< Check if unsigned long int can hold a signaling nan + static constexpr bool has_denorm = false; //!< Check if unsigned long int denormalizes + static constexpr bool has_denorm_loss = false; //!< Check if unsigned long int has precision loss when denormalized + static constexpr bool is_iec559 = false; //!< Check if unsigned long int represents an IEC 559 or IEEE 754 + static constexpr bool is_bounded = true; //!< Check if unsigned long int represents a finite set of values + static constexpr bool is_modulo = true; //!< Check if unsigned long int can handle modulo arithmetic + static constexpr bool tinyness_before = false; //!< Check if unsigned long int checks for tinyness before rounding + static constexpr bool traps = true; //!< Check if unsigned long int can cause operations to trap - static constexpr int digits = ULONG_RADIX_DIG; - static constexpr int digits10 = ULONG_DIG; - static constexpr int max_digits10 = ULONG_DECIMAL_DIG; - static constexpr int radix = ULONG_RADIX; - static constexpr int min_exponent = 0; - static constexpr int min_exponent10 = 0; - static constexpr int max_exponent = 0; - static constexpr int max_exponent10 = 0; + static constexpr int digits = ULONG_RADIX_DIG; //!< Get the base representation of the type + static constexpr int digits10 = ULONG_DIG; //!< Get the number of radix digits unsigned long int represents + static constexpr int max_digits10 = ULONG_DECIMAL_DIG; //!< Get the number of decimal digits unsigned long int represents + static constexpr int radix = ULONG_RADIX; //!< Get the maximum number of decimal digits unsigned long int represents + static constexpr int min_exponent = 0; //!< Get the minimum number of radix digits that represent the exponent of unsigned long int + static constexpr int min_exponent10 = 0; //!< Get the minimum number of decimal digits that represent the exponent of unsigned long int + static constexpr int max_exponent = 0; //!< Get the maximum number of radix digits that represent the exponent of unsigned long int + static constexpr int max_exponent10 = 0; //!< Get the maximum number of decimal digits that represent the exponent of unsigned long int - static constexpr unsigned long min() { return ULONG_MIN; } - static constexpr unsigned long max() { return ULONG_MAX; } - static constexpr unsigned long lowest() { return 1; } - static constexpr unsigned long epsilon() { return 1; } - static constexpr unsigned long round_error() { return 0; } - static constexpr unsigned long infinity() { return 0; } - static constexpr unsigned long quiet_NaN() { return 0; } - static constexpr unsigned long signaling_NaN() { return 0; } - static constexpr unsigned long denorm_min() { return 0; } + static constexpr unsigned long min() { return ULONG_MIN; } //!< \returns the minimum finite value of unsigned long int + static constexpr unsigned long max() { return ULONG_MAX; } //!< \returns the maximum finite value of unsigned long int + static constexpr unsigned long lowest() { return 1; } //!< \returns the smallest positive value of unsigned long int + static constexpr unsigned long epsilon() { return 1; } //!< \returns the difference between 1.0 and the next representable value + static constexpr unsigned long round_error() { return 0; } //!< \returns the max rounding error of unsigned long int + static constexpr unsigned long infinity() { return 0; } //!< \returns a value of unsigned long int holding a positive infinity + static constexpr unsigned long quiet_NaN() { return 0; } //!< \returns a value of unsigned long int holding a quiet NaN + static constexpr unsigned long signaling_NaN() { return 0; } //!< \returns a value of unsigned long int holding a signaling NaN + static constexpr unsigned long denorm_min() { return 0; } //!< \returns a value of unsigned long int holding the smallest positive subnormal }; -// Overload for the builtin signed char type +/// +/// \brief Definition for type \emph{long long}. template<> struct numeric_limits { - static constexpr bool is_specialized = true; - static constexpr bool is_signed = true; - static constexpr bool is_integer = true; - static constexpr bool is_exact = true; - static constexpr bool has_infinity = false; - static constexpr bool has_quiet_nan = false; - static constexpr bool has_signaling_nan = false; - static constexpr bool has_denorm = false; - static constexpr bool has_denorm_loss = false; - static constexpr bool is_iec559 = false; - static constexpr bool is_bounded = true; - static constexpr bool is_modulo = true; - static constexpr bool tinyness_before = false; - static constexpr bool traps = true; + static constexpr bool is_specialized = true; //!< Check if the template is specialized for long long + static constexpr bool is_signed = true; //!< Check if long long is signed + static constexpr bool is_integer = true; //!< Check if long long is of an integral type + static constexpr bool is_exact = true; //!< Check if long long is exact in its precision + static constexpr bool has_infinity = false; //!< Check if long long can hold a value representing infinity + static constexpr bool has_quiet_nan = false; //!< Check if long long can hold a non-signaling nan + static constexpr bool has_signaling_nan = false; //!< Check if long long can hold a signaling nan + static constexpr bool has_denorm = false; //!< Check if long long denormalizes + static constexpr bool has_denorm_loss = false; //!< Check if long long has precision loss when denormalized + static constexpr bool is_iec559 = false; //!< Check if long long represents an IEC 559 or IEEE 754 + static constexpr bool is_bounded = true; //!< Check if long long represents a finite set of values + static constexpr bool is_modulo = true; //!< Check if long long can handle modulo arithmetic + static constexpr bool tinyness_before = false; //!< Check if long long checks for tinyness before rounding + static constexpr bool traps = true; //!< Check if long long can cause operations to trap - static constexpr int digits = LLONG_RADIX_DIG; - static constexpr int digits10 = LLONG_DIG; - static constexpr int max_digits10 = LLONG_DECIMAL_DIG; - static constexpr int radix = LLONG_RADIX; - static constexpr int min_exponent = 0; - static constexpr int min_exponent10 = 0; - static constexpr int max_exponent = 0; - static constexpr int max_exponent10 = 0; + static constexpr int digits = LLONG_RADIX_DIG; //!< Get the base representation of the type + static constexpr int digits10 = LLONG_DIG; //!< Get the number of radix digits long long represents + static constexpr int max_digits10 = LLONG_DECIMAL_DIG; //!< Get the number of decimal digits long long represents + static constexpr int radix = LLONG_RADIX; //!< Get the maximum number of decimal digits long long represents + static constexpr int min_exponent = 0; //!< Get the minimum number of radix digits that represent the exponent of long long + static constexpr int min_exponent10 = 0; //!< Get the minimum number of decimal digits that represent the exponent of long long + static constexpr int max_exponent = 0; //!< Get the maximum number of radix digits that represent the exponent of long long + static constexpr int max_exponent10 = 0; //!< Get the maximum number of decimal digits that represent the exponent of long long - static constexpr long long min() { return LLONG_MIN; } - static constexpr long long max() { return LLONG_MAX; } - static constexpr long long lowest() { return 1; } - static constexpr long long epsilon() { return 1; } - static constexpr long long round_error() { return 0; } - static constexpr long long infinity() { return 0; } - static constexpr long long quiet_NaN() { return 0; } - static constexpr long long signaling_NaN() { return 0; } - static constexpr long long denorm_min() { return 0; } + static constexpr long long min() { return LLONG_MIN; } //!< \returns the minimum finite value of long long + static constexpr long long max() { return LLONG_MAX; } //!< \returns the maximum finite value of long long + static constexpr long long lowest() { return 1; } //!< \returns the smallest positive value of long long + static constexpr long long epsilon() { return 1; } //!< \returns the difference between 1.0 and the next representable value + static constexpr long long round_error() { return 0; } //!< \returns the max rounding error of long long + static constexpr long long infinity() { return 0; } //!< \returns a value of long long holding a positive infinity + static constexpr long long quiet_NaN() { return 0; } //!< \returns a value of long long holding a quiet NaN + static constexpr long long signaling_NaN() { return 0; } //!< \returns a value of long long holding a signaling NaN + static constexpr long long denorm_min() { return 0; } //!< \returns a value of long long holding the smallest positive subnormal }; -// Overload for the builtin signed char type +/// +/// \brief Definition for type \emph{unsigned long long}. template<> struct numeric_limits { - static constexpr bool is_specialized = true; - static constexpr bool is_signed = false; - static constexpr bool is_integer = true; - static constexpr bool is_exact = true; - static constexpr bool has_infinity = false; - static constexpr bool has_quiet_nan = false; - static constexpr bool has_signaling_nan = false; - static constexpr bool has_denorm = false; - static constexpr bool has_denorm_loss = false; - static constexpr bool is_iec559 = false; - static constexpr bool is_bounded = true; - static constexpr bool is_modulo = true; - static constexpr bool tinyness_before = false; - static constexpr bool traps = true; + static constexpr bool is_specialized = true; //!< Check if the template is specialized for unsigned long long + static constexpr bool is_signed = false; //!< Check if unsigned long long is signed + static constexpr bool is_integer = true; //!< Check if unsigned long long is of an integral type + static constexpr bool is_exact = true; //!< Check if unsigned long long is exact in its precision + static constexpr bool has_infinity = false; //!< Check if unsigned long long can hold a value representing infinity + static constexpr bool has_quiet_nan = false; //!< Check if unsigned long long can hold a non-signaling nan + static constexpr bool has_signaling_nan = false; //!< Check if unsigned long long can hold a signaling nan + static constexpr bool has_denorm = false; //!< Check if unsigned long long denormalizes + static constexpr bool has_denorm_loss = false; //!< Check if unsigned long long has precision loss when denormalized + static constexpr bool is_iec559 = false; //!< Check if unsigned long long represents an IEC 559 or IEEE 754 + static constexpr bool is_bounded = true; //!< Check if unsigned long long represents a finite set of values + static constexpr bool is_modulo = true; //!< Check if unsigned long long can handle modulo arithmetic + static constexpr bool tinyness_before = false; //!< Check if unsigned long long checks for tinyness before rounding + static constexpr bool traps = true; //!< Check if unsigned long long can cause operations to trap - static constexpr int digits = ULLONG_RADIX_DIG; - static constexpr int digits10 = ULLONG_DIG; - static constexpr int max_digits10 = ULLONG_DECIMAL_DIG; - static constexpr int radix = ULLONG_RADIX; - static constexpr int min_exponent = 0; - static constexpr int min_exponent10 = 0; - static constexpr int max_exponent = 0; - static constexpr int max_exponent10 = 0; + static constexpr int digits = ULLONG_RADIX_DIG; //!< Get the base representation of the type + static constexpr int digits10 = ULLONG_DIG; //!< Get the number of radix digits unsigned long long represents + static constexpr int max_digits10 = ULLONG_DECIMAL_DIG; //!< Get the number of decimal digits unsigned long long represents + static constexpr int radix = ULLONG_RADIX; //!< Get the maximum number of decimal digits unsigned long long represents + static constexpr int min_exponent = 0; //!< Get the minimum number of radix digits that represent the exponent of unsigned long long + static constexpr int min_exponent10 = 0; //!< Get the minimum number of decimal digits that represent the exponent of unsigned long long + static constexpr int max_exponent = 0; //!< Get the maximum number of radix digits that represent the exponent of unsigned long long + static constexpr int max_exponent10 = 0; //!< Get the maximum number of decimal digits that represent the exponent of unsigned long long - static constexpr unsigned long long min() { return ULLONG_MIN; } - static constexpr unsigned long long max() { return ULLONG_MAX; } - static constexpr unsigned long long lowest() { return 1; } - static constexpr unsigned long long epsilon() { return 1; } - static constexpr unsigned long long round_error() { return 0; } - static constexpr unsigned long long infinity() { return 0; } - static constexpr unsigned long long quiet_NaN() { return 0; } - static constexpr unsigned long long signaling_NaN() { return 0; } - static constexpr unsigned long long denorm_min() { return 0; } + static constexpr unsigned long long min() { return ULLONG_MIN; } //!< \returns the minimum finite value of unsigned long long + static constexpr unsigned long long max() { return ULLONG_MAX; } //!< \returns the maximum finite value of unsigned long long + static constexpr unsigned long long lowest() { return 1; } //!< \returns the smallest positive value of unsigned long long + static constexpr unsigned long long epsilon() { return 1; } //!< \returns the difference between 1.0 and the next representable value + static constexpr unsigned long long round_error() { return 0; } //!< \returns the max rounding error of unsigned long long + static constexpr unsigned long long infinity() { return 0; } //!< \returns a value of unsigned long long holding a positive infinity + static constexpr unsigned long long quiet_NaN() { return 0; } //!< \returns a value of unsigned long long holding a quiet NaN + static constexpr unsigned long long signaling_NaN() { return 0; } //!< \returns a value of unsigned long long holding a signaling NaN + static constexpr unsigned long long denorm_min() { return 0; } //!< \returns a value of unsigned long long holding the smallest positive subnormal }; } diff --git a/include/fennec/lang/metasequences.h b/include/fennec/lang/metasequences.h index 9a5df0d..c393734 100644 --- a/include/fennec/lang/metasequences.h +++ b/include/fennec/lang/metasequences.h @@ -80,7 +80,7 @@ namespace fennec /// /// \brief metaprogramming sequence /// -/// \details Stores a sequence of values of type \f$ValueT\f$ as a template pack. +/// \details Stores a sequence of values of type \emph{ValueT} as a template pack. /// You can access the parameter pack in another template function, i.e. /// \code{cpp} /// template @@ -138,7 +138,7 @@ struct integer_metasequence : metasequence /// -/// \brief generate a fennec::integer_metasequence \f$\left[\,0\,\ldots\,N\,\right)\f$ +/// \brief generate a fennec::integer_metasequence \math{\left[\,0\,\ldots\,N\,\right)} /// /// \details /// \tparam IntT type of the values, must satisfy `fennec::is_integral` @@ -177,7 +177,7 @@ template struct index_metasequence : integer_metasequence` diff --git a/include/fennec/lang/ranges.h b/include/fennec/lang/ranges.h index 098e4f7..93771f9 100644 --- a/include/fennec/lang/ranges.h +++ b/include/fennec/lang/ranges.h @@ -32,12 +32,13 @@ #define FENNEC_LANG_RANGES_H #include +#include namespace fennec { /// -/// \brief C++ Iterator Specification \f$begin()\f$ +/// \brief C++ Iterator Specification \emph{begin()} /// \tparam ContainerT the container type /// \param c the container to iterate on /// \returns an iterator at the start of the container @@ -47,7 +48,7 @@ inline constexpr auto begin(ContainerT& c) noexcept(noexcept(c.begin())) -> decl } /// -/// \brief C++ Iterator Specification \f$begin()\f$ +/// \brief C++ Iterator Specification \emph{begin()} /// \tparam ContainerT the container type /// \param c the container to iterate on /// \returns an iterator at the start of the container @@ -57,7 +58,7 @@ inline constexpr auto begin(const ContainerT& c) noexcept(noexcept(c.begin())) - } /// -/// \brief C++ Iterator Specification \f$begin()\f$ +/// \brief C++ Iterator Specification \emph{begin()} /// \tparam T the element type /// \tparam N the bounds of the array /// \param arr a bounded array to iterate on @@ -69,7 +70,7 @@ inline constexpr T* begin(T (&arr)[N]) noexcept { /// -/// \brief C++ Iterator Specification \f$end()\f$ +/// \brief C++ Iterator Specification \emph{end()} /// \tparam ContainerT the container type /// \param c the container to iterate on /// \returns an iterator at the end of the container @@ -79,7 +80,7 @@ inline constexpr auto end(ContainerT& c) noexcept(noexcept(c.end())) -> decltype } /// -/// \brief C++ Iterator Specification \f$end()\f$ +/// \brief C++ Iterator Specification \emph{end()} /// \tparam ContainerT the container type /// \param c the container to iterate on /// \returns an iterator at the end of the container @@ -89,7 +90,7 @@ inline constexpr auto end(const ContainerT& c) noexcept(noexcept(c.end())) -> de } /// -/// \brief C++ Iterator Specification \f$end()\f$ +/// \brief C++ Iterator Specification \emph{end()} /// \tparam T the element type /// \tparam N the bounds of the array /// \param arr a bounded array to iterate on @@ -99,6 +100,129 @@ inline constexpr T* end(T (&arr)[N]) noexcept { return arr + N; } +/// +/// \brief Range for array types. +/// \tparam TypeT The base type. +/// +/// \note Operates on the range \emph{[first, last)}. +template +struct range { + TypeT* first; //!< The first element + TypeT* last; //!< The last element + + /// + /// \brief C++ Iterator Specification \emph{begin()} + /// \returns A pointer to the start of the array + TypeT* begin() const { + return first; + } + + /// + /// \brief C++ Iterator Specification \emph{end()} + /// \returns A pointer to the start of the array + TypeT* end() const { + return last; + } +}; + +/// +/// \brief Range for iterators. +/// \tparam IteratorT The iterator type. +/// +/// \note Operates on the range \emph{[first, last)}. +template requires(is_iterable_v) +struct range { + IteratorT first; //!< The first element + IteratorT last; //!< The last element + + /// + /// \brief C++ Iterator Specification \emph{begin()} + /// \returns A pointer to the start of the array + IteratorT& begin() const { + return first; + } + + /// + /// \brief C++ Iterator Specification \emph{end()} + /// \returns A pointer to the start of the array + IteratorT& end() const { + return last; + } +}; + + +/// +/// \brief Proxy Struct for fulfilling the C++ 11 Iterator Specification +template +struct counter { + ScalarT val; //!< The held value + + /// + /// \brief Pre-Increment + /// \returns A reference to \emph{this} after incrementing \emph{val}. + counter& operator++() { + ++val; + return *this; + } + + /// + /// \brief Post-Increment + /// \returns A counter with the previously held value. + counter operator++(int) { + ++val; + return { val - 1 }; + } + + /// + /// \brief Equality Operator + /// \param ctr The counter to compare with + /// \returns \math{{val}_{this} = {val}_{ctr}} + bool operator==(const counter& ctr) const { + return val == ctr.val; + } + + /// + /// \brief Equality Operator + /// \param ctr The counter to compare with + /// \returns \math{{val}_{this} \neq {val}_{ctr}} + bool operator!=(const counter& ctr) const { + return val != ctr.val; + } + + /// + /// \brief Dereference Operator + /// \returns \emph{val} + ScalarT operator*() const { + return val; + } +}; + + +/// +/// \brief Range for scalar types. +/// \tparam ScalarT The scalar type. +/// +/// \note Operates on the range \emph{[first, last)}. +template requires(is_scalar_v) +struct range { + ScalarT first; //!< The starting value + ScalarT last; //!< The last value + + /// + /// \brief C++ Iterator Specification \emph{begin()} + /// \returns A `fennec::counter` containing \emph{first} + counter begin() const { + return { first }; + } + + /// + /// \brief C++ Iterator Specification \emph{begin()} + /// \returns A `fennec::counter` containing \emph{last} + counter end() const { + return { last }; + } +}; + } #endif // FENNEC_LANG_RANGES_H \ No newline at end of file diff --git a/include/fennec/core/system.h b/include/fennec/lang/system.h similarity index 64% rename from include/fennec/core/system.h rename to include/fennec/lang/system.h index f136842..31c22ab 100644 --- a/include/fennec/core/system.h +++ b/include/fennec/lang/system.h @@ -1,6 +1,6 @@ // ===================================================================================================================== // fennec, a free and open source game engine -// Copyright © 2025 - 2026 Medusa Slockbower +// Copyright © 2025 Medusa Slockbower // // This program is free software: you can redistribute it and/or modify // it under the terms of the GNU General Public License as published by @@ -16,32 +16,29 @@ // along with this program. If not, see . // ===================================================================================================================== -#ifndef FENNEC_CORE_SYSTEM_H -#define FENNEC_CORE_SYSTEM_H -#include +/// +/// \file system.h +/// \brief +/// +/// +/// \details +/// \author Medusa Slockbower +/// +/// \copyright Copyright © 2025 - 2026 Medusa Slockbower ([GPLv3](https://www.gnu.org/licenses/gpl-3.0.en.html)) +/// +/// + + +#ifndef FENNEC_LANG_SYSTEM_H +#define FENNEC_LANG_SYSTEM_H + +#include namespace fennec { -class system { -public: - using tick_f = void (*)(system*, double); - using frame_f = void (*)(system*, size_t); - - const string name; - const tick_f tick; - const frame_f frame; - - system(const cstring& name, tick_f tick, frame_f frame) - : name(name), tick(tick), frame(frame) { - } - - virtual ~system() = default; - - virtual void init() = 0; - virtual void shutdown() = 0; -}; +using ::system; } -#endif // FENNEC_CORE_SYSTEM_H +#endif // FENNEC_LANG_SYSTEM_H \ No newline at end of file diff --git a/include/fennec/lang/type_sequences.h b/include/fennec/lang/type_sequences.h index b0707c0..b242855 100644 --- a/include/fennec/lang/type_sequences.h +++ b/include/fennec/lang/type_sequences.h @@ -102,7 +102,7 @@ template using nth_element_t = nth_element` and replace the first \f$ArgT\f$ of `ArgsT...` with \f$SubT\f$ +/// \brief Take a Template with a Pack `ClassT` and replace the first \emph{ArgT} of \emph{ArgsT...} with \emph{SubT} template struct replace_first_element { }; #ifndef FENNEC_DOXYGEN @@ -134,7 +134,7 @@ template constexpr size_t max_element_size_v = max_element_size struct find_element : detail::_find_element<0, T, Ts...> {}; @@ -180,7 +180,7 @@ struct search_element_args, TypesT...> // fennec::contains_element ============================================================================================ /// -/// \brief Checks if the type sequence `Ts...` contains \f$T\f$ +/// \brief Checks if the type sequence \emph{Ts...} contains \emph{T} /// \tparam T The type to find /// \tparam Ts The type sequence to check template struct contains_element : bool_constant<(is_same_v or ...)> {}; diff --git a/include/fennec/lang/type_traits.h b/include/fennec/lang/type_traits.h index 59262dc..434249c 100644 --- a/include/fennec/lang/type_traits.h +++ b/include/fennec/lang/type_traits.h @@ -436,7 +436,7 @@ namespace fennec /// /// \brief metaprogramming helper for determining if a function is consteval -/// \returns \f$true\f$ if under `consteval`, \f$false\f$ otherwise +/// \returns \emph{true} if under `consteval`, \emph{false} otherwise constexpr inline bool is_constant_evaluated() noexcept { if consteval { return true; @@ -461,7 +461,7 @@ template struct is_void : detail::_is_void>{}; /// -/// \brief Shorthand for ```is_void::value``` +/// \brief Shorthand for `(.*?)` /// \tparam T type to check template constexpr bool_t is_void_v = is_void::value; @@ -478,7 +478,7 @@ template struct is_null_pointer : detail::_is_null_pointer>{}; /// -/// \brief Shorthand for ```is_null_pointer::value``` +/// \brief Shorthand for `(.*?)` /// \tparam T type to check template constexpr bool_t is_null_pointer_v = is_null_pointer::value; @@ -495,7 +495,7 @@ template struct is_bool : detail::_is_bool>{}; /// -/// \brief Shorthand for ```is_bool::value``` +/// \brief Shorthand for `(.*?)` /// \tparam T type to check template constexpr bool_t is_bool_v = is_bool::value; @@ -512,7 +512,7 @@ template struct is_integral : detail::_is_integral> {}; /// -/// \brief Shorthand for ```is_integral::value``` +/// \brief Shorthand for `(.*?)` /// \tparam T type to check template constexpr bool_t is_integral_v = is_integral::value; @@ -529,7 +529,7 @@ template struct is_floating_point : detail::_is_floating_point>{}; /// -/// \brief Shorthand for ```is_floating_point::value``` +/// \brief Shorthand for `(.*?)` /// \tparam T type to check template constexpr bool_t is_floating_point_v = is_floating_point {}; @@ -564,7 +564,7 @@ template struct is_array #endif /// -/// \brief Shorthand for ```is_array::value``` +/// \brief Shorthand for `(.*?)` /// \tparam T type to check template constexpr bool_t is_array_v = is_array::value; @@ -641,7 +641,7 @@ template struct is_pointer : detail::_is_pointer>{}; /// -/// \brief Shorthand for ```is_pointer::value``` +/// \brief Shorthand for `(.*?)` /// \tparam T type to check template constexpr bool_t is_pointer_v = is_pointer {}; @@ -652,13 +652,13 @@ template constexpr bool_t is_pointer_v = is_pointer {}; /// /// \brief Check if \p T is of a floating point type /// -/// \details Checks if type \f$T\f$ is a floating point type and store it in `is_same::value`. +/// \details Checks if type \emph{T} is a floating point type and store it in `is_same::value`. /// \tparam T type to check template struct is_lvalue_reference : detail::_is_lvalue_reference{}; /// -/// \brief Shorthand for ```is_floating_point::value``` +/// \brief Shorthand for `(.*?)` /// \tparam T type to check template constexpr bool_t is_lvalue_reference_v = is_lvalue_reference {}; @@ -669,13 +669,13 @@ template constexpr bool_t is_lvalue_reference_v = is_lvalue_referenc /// /// \brief Check if \p T is of a floating point type /// -/// \details Checks if type \f$T\f$ is a floating point type and store it in `is_same::value`. +/// \details Checks if type \emph{T} is a floating point type and store it in `is_same::value`. /// \tparam T type to check template struct is_rvalue_reference : detail::_is_rvalue_reference{}; /// -/// \brief Shorthand for ```is_floating_point::value``` +/// \brief Shorthand for `(.*?)` /// \tparam T type to check template constexpr bool_t is_rvalue_reference_v = is_rvalue_reference {}; @@ -686,13 +686,13 @@ template constexpr bool_t is_rvalue_reference_v = is_rvalue_referenc /// /// \brief Check if \p T is a pointer to a member function /// -/// \details Checks if type \f$T\f$ is pointer to a member function and store it in `is_member_function_pointer::value`. +/// \details Checks if type \emph{T} is pointer to a member function and store it in `is_member_function_pointer::value`. /// \tparam T type to check template struct is_member_function_pointer : bool_constant {}; /// -/// \brief Shorthand for ```is_member_function_pointer::value``` +/// \brief Shorthand for `(.*?)` /// \tparam T type to check template constexpr bool_t is_member_function_pointer_v = is_member_function_pointer {}; @@ -703,13 +703,13 @@ template constexpr bool_t is_member_function_pointer_v = is_member_f /// /// \brief Check if \p T is a pointer to a member object /// -/// \details Checks if type \f$T\f$ is pointer to a member object and store it in `is_member_object_pointer::value`. +/// \details Checks if type \emph{T} is pointer to a member object and store it in `is_member_object_pointer::value`. /// \tparam T type to check template struct is_member_object_pointer : bool_constant {}; /// -/// \brief Shorthand for ```is_member_object_pointer::value``` +/// \brief Shorthand for `(.*?)` /// \tparam T type to check template constexpr bool_t is_member_object_pointer_v = is_member_object_pointer {}; @@ -725,13 +725,13 @@ template constexpr bool_t is_member_object_pointer_v = is_member_obj /// /// \brief Check if \p T is an arithmetic type /// -/// \details Checks if type \f$T\f$ is a built-in type with arithmetic operators and store it in `is_same::value`. +/// \details Checks if type \emph{T} is a built-in type with arithmetic operators and store it in `is_same::value`. /// \tparam T type to check template struct is_arithmetic : bool_constant or is_floating_point_v>{}; /// -/// \brief Shorthand for ```is_arithmetic::value``` +/// \brief Shorthand for `(.*?)` /// \tparam T type to check template constexpr bool_t is_arithmetic_v = is_arithmetic::value; @@ -745,7 +745,7 @@ template struct is_fundamental : bool_constant or is_void_v or is_null_pointer_v>{}; /// -/// \brief Shorthand for ```is_fundamental::value``` +/// \brief Shorthand for `(.*?)` /// \tparam T type to check template constexpr bool_t is_fundamental_v = is_fundamental::value; @@ -756,13 +756,13 @@ template constexpr bool_t is_fundamental_v = is_fundamental::valu /// /// \brief Check if \p T is an arithmetic type /// -/// \details Checks if type \f$T\f$ is a built-in type with arithmetic operators and store it in `is_scalar::value`. +/// \details Checks if type \emph{T} is a built-in type with arithmetic operators and store it in `is_scalar::value`. /// \tparam T type to check template struct is_scalar : bool_constant or is_enum_v or is_pointer_v>{}; /// -/// \brief Shorthand for ```is_scalar::value``` +/// \brief Shorthand for `(.*?)` /// \tparam T type to check template constexpr bool_t is_scalar_v = is_scalar::value; @@ -773,12 +773,12 @@ template constexpr bool_t is_scalar_v = is_scalar::value; /// /// \brief Check if \p T is an object /// -/// \details Checks if type \f$T\f$ is an object and store it in `is_object::value`. +/// \details Checks if type \emph{T} is an object and store it in `is_object::value`. /// \tparam T type to check template struct is_object : bool_constant {}; /// -/// \brief Shorthand for ```is_object::value``` +/// \brief Shorthand for `(.*?)` /// \tparam T type to check template constexpr bool_t is_object_v = is_object::value; @@ -789,12 +789,12 @@ template constexpr bool_t is_object_v = is_object::value; /// /// \brief Check if \p T is a object compound type /// -/// \details Checks if type \f$T\f$ is an object and store it in `is_compound::value`. +/// \details Checks if type \emph{T} is an object and store it in `is_compound::value`. /// \tparam T type to check template struct is_compound : bool_constant> {}; /// -/// \brief Shorthand for ```is_compound::value``` +/// \brief Shorthand for `(.*?)` /// \tparam T type to check template constexpr bool_t is_compound_v = is_compound::value; @@ -805,13 +805,13 @@ template constexpr bool_t is_compound_v = is_compound::value; /// /// \brief Check if \p T is of a reference type /// -/// \details Checks if type \f$T\f$ is a reference type and store it in `is_reference::value`. +/// \details Checks if type \emph{T} is a reference type and store it in `is_reference::value`. /// \tparam T type to check template struct is_reference : detail::_is_reference{}; /// -/// \brief Shorthand for ```is_reference::value``` +/// \brief Shorthand for `(.*?)` /// \tparam T type to check template constexpr bool_t is_reference_v = is_reference {}; @@ -822,13 +822,13 @@ template constexpr bool_t is_reference_v = is_reference {}; /// /// \brief Check if \p T is a pointer to a member /// -/// \details Checks if type \f$T\f$ is pointer to a member and store it in `is_member_function_pointer::value`. +/// \details Checks if type \emph{T} is pointer to a member and store it in `is_member_function_pointer::value`. /// \tparam T type to check template struct is_member_pointer : bool_constant {}; /// -/// \brief Shorthand for ```is_member_function_pointer::value``` +/// \brief Shorthand for `(.*?)` /// \tparam T type to check template constexpr bool_t is_member_pointer_v = is_member_pointer {}; @@ -844,13 +844,13 @@ template constexpr bool_t is_member_pointer_v = is_member_pointer /// /// \brief Check if \p T is of a const type /// -/// \details Checks if type \f$T\f$ is a const type and store it in `is_same::value`. +/// \details Checks if type \emph{T} is a const type and store it in `is_same::value`. /// \tparam T type to check template struct is_const : detail::_is_const{}; /// -/// \brief Shorthand for ```is_const::value``` +/// \brief Shorthand for `(.*?)` /// \tparam T type to check template constexpr bool_t is_const_v = is_const {}; @@ -861,13 +861,13 @@ template constexpr bool_t is_const_v = is_const {}; /// /// \brief Check if \p T is of a volatile type /// -/// \details Checks if type \f$T\f$ is a volatile type and store it in `is_same::value`. +/// \details Checks if type \emph{T} is a volatile type and store it in `is_same::value`. /// \tparam T type to check template struct is_volatile : detail::_is_volatile{}; /// -/// \brief Shorthand for ```is_volatile::value``` +/// \brief Shorthand for `(.*?)` /// \tparam T type to check template constexpr bool_t is_volatile_v = is_volatile {}; @@ -876,9 +876,9 @@ template constexpr bool_t is_volatile_v = is_volatile {}; // fennec::is_trivial -------------------------------------------------------------------------------------------------- /// -/// \brief Check if type \f$T\f$ is trivial +/// \brief Check if type \emph{T} is trivial /// -/// \details Checks if \f$T\f$ +/// \details Checks if \emph{T} /// \tparam T type to check template struct is_trivial : bool_constant {}; @@ -892,9 +892,9 @@ template constexpr bool_t is_trivial_v = is_trivial{}; // fennec::is_trivially_copyable --------------------------------------------------------------------------------------- /// -/// \brief Check if type \f$T\f$ is trivially_copyable +/// \brief Check if type \emph{T} is trivially_copyable /// -/// \details Checks if \f$T\f$ +/// \details Checks if \emph{T} /// \tparam T type to check template struct is_trivially_copyable : bool_constant {}; @@ -908,9 +908,9 @@ template constexpr bool_t is_trivially_copyable_v = is_trivially_cop // fennec::is_standard_layout ------------------------------------------------------------------------------------------ /// -/// \brief Check if type \f$T\f$ is standard_layout +/// \brief Check if type \emph{T} is standard_layout /// -/// \details Checks if \f$T\f$ +/// \details Checks if \emph{T} /// \tparam T type to check template struct is_standard_layout : bool_constant {}; @@ -924,9 +924,9 @@ template constexpr bool_t is_standard_layout_v = is_standard_layout< // fennec::has_unique_object_representations --------------------------------------------------------------------------- /// -/// \brief Check if type \f$T\f$ has unique object representations +/// \brief Check if type \emph{T} has unique object representations /// -/// \details Checks if \f$T\f$ +/// \details Checks if \emph{T} /// \tparam T type to check template struct has_unique_object_representations : bool_constant)> {}; @@ -941,9 +941,9 @@ template constexpr bool_t has_unique_object_representations_v = has_ // fennec::is_empty ---------------------------------------------------------------------------------------------------- /// -/// \brief Check if type \f$T\f$ is empty +/// \brief Check if type \emph{T} is empty /// -/// \details Checks if \f$T\f$ +/// \details Checks if \emph{T} /// \tparam T type to check template struct is_empty : bool_constant {}; @@ -957,9 +957,9 @@ template constexpr bool_t is_empty_v = is_empty{}; // fennec::is_polymorphic ---------------------------------------------------------------------------------------------- /// -/// \brief Check if type \f$T\f$ is polymorphic +/// \brief Check if type \emph{T} is polymorphic /// -/// \details Checks if \f$T\f$ +/// \details Checks if \emph{T} /// \tparam T type to check template struct is_polymorphic : bool_constant {}; @@ -973,9 +973,9 @@ template constexpr bool_t is_polymorphic_v = is_polymorphic{}; // fennec::is_abstract ------------------------------------------------------------------------------------------------- /// -/// \brief Check if type \f$T\f$ is abstract +/// \brief Check if type \emph{T} is abstract /// -/// \details Checks if \f$T\f$ +/// \details Checks if \emph{T} /// \tparam T type to check template struct is_abstract : bool_constant {}; @@ -989,9 +989,9 @@ template constexpr bool_t is_abstract_v = is_abstract{}; // fennec::is_complete ------------------------------------------------------------------------------------------------- /// -/// \brief Check if type \f$T\f$ is complete +/// \brief Check if type \emph{T} is complete /// -/// \details Checks if \f$T\f$ +/// \details Checks if \emph{T} /// \tparam T type to check template struct is_complete : detail::_is_complete::type {}; @@ -1005,9 +1005,9 @@ template constexpr bool_t is_complete_v = is_complete{}; // fennec::is_final ------------------------------------------------------------------------------------------------- /// -/// \brief Check if type \f$T\f$ is final +/// \brief Check if type \emph{T} is final /// -/// \details Checks if \f$T\f$ +/// \details Checks if \emph{T} /// \tparam T type to check template struct is_final : bool_constant {}; @@ -1021,9 +1021,9 @@ template constexpr bool_t is_final_v = is_final{}; // fennec::is_aggregate ------------------------------------------------------------------------------------------------- /// -/// \brief Check if type \f$T\f$ is aggregate +/// \brief Check if type \emph{T} is aggregate /// -/// \details Checks if \f$T\f$ +/// \details Checks if \emph{T} /// \tparam T type to check template struct is_aggregate : bool_constant {}; @@ -1040,13 +1040,13 @@ template constexpr bool_t is_aggregate_v = is_aggregate{}; /// /// \brief Check if \p T is of a signed integral /// -/// \details Checks if type \f$T\f$ is a signed type i.e. `T(-1) < T(0)` and stores it in `is_same::value`. +/// \details Checks if type \emph{T} is a signed type i.e. \math{\textbf{T(-1)} < \textbf{T(0)}} and stores it in `is_same::value`. /// \tparam T type to check template struct is_signed : detail::_is_signed> {}; /// -/// \brief Shorthand for ```is_signed::value``` +/// \brief Shorthand for `(.*?)` /// \tparam T type to check template constexpr bool_t is_signed_v = is_signed::value; @@ -1058,13 +1058,13 @@ template constexpr bool_t is_signed_v = is_signed::value; /// /// \brief Check if \p T is of an unsigned integral /// -/// \details Checks if type \f$T\f$ is an unsigned type i.e. `T(-1) > T(0)` and stores it in `is_same::value`. +/// \details Checks if type \emph{T} is an unsigned type i.e. \math{\textbf{T(-1)} > \textbf{T(0)}} and stores it in `is_same::value`. /// \tparam T type to check template struct is_unsigned : detail::_is_unsigned> {}; /// -/// \brief Shorthand for ```is_unsigned::value``` +/// \brief Shorthand for `(.*?)` /// \tparam T type to check template constexpr bool_t is_unsigned_v = is_unsigned::value; @@ -1072,16 +1072,6 @@ template struct is_unsigned // fennec::is_bounded_array -------------------------------------------------------------------------------------------- -#if FENNEC_HAS_BUILTIN_BOUNDED_ARRAY - -/// -/// \brief Check if \p T is of a bounded array type -/// \tparam T type to check -template struct is_bounded_array - : bool_constant {}; - -#else - /// /// \brief Check if \p T is of an bounded type /// \tparam T type to check @@ -1092,10 +1082,8 @@ template struct is_bounded_array template struct is_bounded_array : true_type {}; -#endif - /// -/// \brief Shorthand for ```is_bounded_array::value``` +/// \brief Shorthand for `(.*?)` /// \tparam T type to check template constexpr bool_t is_bounded_array_v = is_bounded_array::value; @@ -1103,16 +1091,6 @@ template constexpr bool_t is_bounded_array_v = is_bounded_array:: // fennec::is_unbounded_array ------------------------------------------------------------------------------------------ -#if FENNEC_HAS_BUILTIN_UNBOUNDED_ARRAY - -/// -/// \brief Check if \p T is of a unbounded array type -/// \tparam T type to check -template struct is_unbounded_array - : bool_constant {}; - -#else - /// /// \brief Check if \p T is of an unbounded type /// \tparam T type to check @@ -1123,10 +1101,8 @@ template struct is_unbounded_array template struct is_unbounded_array : true_type {}; -#endif - /// -/// \brief Shorthand for ```is_unbounded_array::value``` +/// \brief Shorthand for `(.*?)` /// \tparam T type to check template constexpr bool_t is_unbounded_array_v = is_unbounded_array::value; @@ -1163,7 +1139,7 @@ struct is_scoped_enum #endif /// -/// \brief Shorthand for ```is_scoped_enum::value``` +/// \brief Shorthand for `(.*?)` /// \tparam T type to check template constexpr bool_t is_scoped_enum_v = is_scoped_enum::value; @@ -1177,9 +1153,9 @@ template constexpr bool_t is_scoped_enum_v = is_scoped_enum::valu // fennec::is_convertible ---------------------------------------------------------------------------------------------- /// -/// \brief Check if type \f$T0\f$ can be converted \f$T1\f$ +/// \brief Check if type \emph{T0} can be converted \emph{T1} /// -/// \details Checks if \f$TypeT0\f$ +/// \details Checks if \emph{TypeT0} /// \tparam FromT First type /// \tparam ToT Second type template struct is_convertible @@ -1196,8 +1172,8 @@ template constexpr bool_t is_convertible_v = is_co // fennec::is_constructible -------------------------------------------------------------------------------------------- /// -/// \brief Check if \f$ClassT\f$ can be constructed with `ArgsT,` i.e. `ClassT(ArgsT...)`. -/// This may be read as "is \f$ClassT\f$ constructible with \f$ArgsT\f$" +/// \brief Check if \emph{ClassT} can be constructed with \emph{ArgsT...}, i.e. `ClassT(ArgsT...)`. +/// This may be read as "is \emph{ClassT} constructible with \emph{ArgsT}" /// \tparam ClassT The class type to test /// \tparam ArgsT The arguments for the specific constructor template struct is_constructible @@ -1212,7 +1188,7 @@ template constexpr bool_t is_constructible_v // fennec::is_trivially_constructible ---------------------------------------------------------------------------------- /// -/// \brief Check if \f$ClassT\f$ is trivially constructible +/// \brief Check if \emph{ClassT} is trivially constructible /// \tparam ClassT The class type to test /// \tparam ArgsT The arguments for the specific constructor template struct is_trivially_constructible @@ -1227,7 +1203,7 @@ template constexpr bool_t is_trivially_constructible_v = is_tri // fennec::is_nothrow_constructible ------------------------------------------------------------------------------------ /// -/// \brief Check if \f$ClassT\f$ is nothrow constructible +/// \brief Check if \emph{ClassT} is nothrow constructible /// \tparam ClassT The class type to test /// \tparam ArgsT The arguments for the specific constructor template struct is_nothrow_constructible @@ -1242,7 +1218,7 @@ template constexpr bool_t is_nothrow_constructible_v = is_nothr // fennec::is_default_constructible ------------------------------------------------------------------------------------ /// -/// \brief Check if \f$ClassT\f$ is default constructible +/// \brief Check if \emph{ClassT} is default constructible /// \tparam ClassT The class type to test template struct is_default_constructible : bool_constant {}; @@ -1256,7 +1232,7 @@ template constexpr bool_t is_default_constructible_v = is_defau // fennec::is_trivially_default_constructible -------------------------------------------------------------------------- /// -/// \brief Check if \f$ClassT\f$ is trivially default constructible +/// \brief Check if \emph{ClassT} is trivially default constructible /// \tparam ClassT The class type to test template struct is_trivially_default_constructible : bool_constant {}; @@ -1270,7 +1246,7 @@ template constexpr bool_t is_trivially_default_constructible_v // fennec::is_nothrow_default_constructible -------------------------------------------------------------------------- /// -/// \brief Check if \f$ClassT\f$ is nothrow default constructible +/// \brief Check if \emph{ClassT} is nothrow default constructible /// \tparam ClassT The class type to test template struct is_nothrow_default_constructible : bool_constant {}; @@ -1284,7 +1260,7 @@ template constexpr bool_t is_nothrow_default_constructible_v = // fennec::is_copy_constructible --------------------------------------------------------------------------------------- /// -/// \brief Check if \f$ClassT\f$ is copy constructible +/// \brief Check if \emph{ClassT} is copy constructible /// \tparam ClassT The class type to test template struct is_copy_constructible : bool_constant)> {}; @@ -1298,7 +1274,7 @@ template constexpr bool_t is_copy_constructib // fennec::is_trivially_copy_constructible ----------------------------------------------------------------------------- /// -/// \brief Check if \f$ClassT\f$ is trivially copy constructible +/// \brief Check if \emph{ClassT} is trivially copy constructible /// \tparam ClassT The class type to test template struct is_trivially_copy_constructible : bool_constant)> {}; @@ -1312,7 +1288,7 @@ template struct is_trivially_copy_constructible // fennec::is_nothrow_copy_constructible ------------------------------------------------------------------------------- /// -/// \brief Check if \f$ClassT\f$ is nothrow copy constructible +/// \brief Check if \emph{ClassT} is nothrow copy constructible /// \tparam ClassT The class type to test template struct is_nothrow_copy_constructible : bool_constant)> {}; @@ -1326,7 +1302,7 @@ template constexpr bool_t is_nothrow_copy_con // fennec::is_move_constructible --------------------------------------------------------------------------------------- /// -/// \brief Check if \f$ClassT\f$ is move constructible +/// \brief Check if \emph{ClassT} is move constructible /// \tparam ClassT The class type to test template struct is_move_constructible : bool_constant)> {}; @@ -1340,7 +1316,7 @@ template constexpr bool_t is_move_constructib // fennec::is_trivially_move_constructible ----------------------------------------------------------------------------- /// -/// \brief Check if \f$ClassT\f$ is trivially move constructible +/// \brief Check if \emph{ClassT} is trivially move constructible /// \tparam ClassT The class type to test template struct is_trivially_move_constructible : bool_constant)> {}; @@ -1354,7 +1330,7 @@ template struct is_trivially_move_constructible // fennec::is_nothrow_move_constructible ------------------------------------------------------------------------------- /// -/// \brief Check if \f$ClassT\f$ is nothrow move constructible +/// \brief Check if \emph{ClassT} is nothrow move constructible /// \tparam ClassT The class type to test template struct is_nothrow_move_constructible : bool_constant)> {}; @@ -1368,7 +1344,7 @@ template constexpr bool_t is_nothrow_move_con // fennec::is_assignable ----------------------------------------------------------------------------------------------- /// -/// \brief Check if \f$ClassT\f$ is assignable +/// \brief Check if \emph{ClassT} is assignable /// \tparam ClassAT The class type to test /// \tparam ClassBT The arguments for the specific constructor template struct is_assignable @@ -1383,7 +1359,7 @@ template constexpr bool_t is_assignable_v = // fennec::is_trivially_assignable ------------------------------------------------------------------------------------- /// -/// \brief Check if \f$ClassT\f$ is trivially assignable +/// \brief Check if \emph{ClassT} is trivially assignable /// \tparam ClassAT The class type to test /// \tparam ClassBT The arguments for the specific constructor template struct is_trivially_assignable @@ -1399,7 +1375,7 @@ template constexpr bool_t is_trivially_assig // fennec::is_nothrow_assignable --------------------------------------------------------------------------------------- /// -/// \brief Check if \f$ClassT\f$ is nothrow assignable +/// \brief Check if \emph{ClassT} is nothrow assignable /// \tparam ClassAT The class type to test /// \tparam ClassBT The arguments for the specific constructor template struct is_nothrow_assignable @@ -1414,7 +1390,7 @@ template constexpr bool_t is_nothrow_assigna // fennec::is_copy_assignable ------------------------------------------------------------------------------------------ /// -/// \brief Check if \f$ClassT\f$ is copy assignable +/// \brief Check if \emph{ClassT} is copy assignable /// \tparam ClassT The class type to test template struct is_copy_assignable : bool_constant, add_lvalue_reference_t)> {}; @@ -1428,7 +1404,7 @@ template constexpr bool_t is_copy_assignable_v = is_copy_assign // fennec::is_trivially_copy_assignable -------------------------------------------------------------------------------- /// -/// \brief Check if \f$ClassT\f$ is trivially_copy assignable +/// \brief Check if \emph{ClassT} is trivially_copy assignable /// \tparam ClassT The class type to test template struct is_trivially_copy_assignable : bool_constant, add_lvalue_reference_t)> {}; @@ -1442,7 +1418,7 @@ template constexpr bool_t is_trivially_copy_assignable_v = is_t // fennec::is_nothrow_copy_assignable ---------------------------------------------------------------------------------- /// -/// \brief Check if \f$ClassT\f$ is nothrow_copy assignable +/// \brief Check if \emph{ClassT} is nothrow_copy assignable /// \tparam ClassT The class type to test template struct is_nothrow_copy_assignable : bool_constant, add_lvalue_reference_t)> {}; @@ -1456,7 +1432,7 @@ template constexpr bool_t is_nothrow_copy_assignable_v = is_not // fennec::is_move_assignable ------------------------------------------------------------------------------------------ /// -/// \brief Check if \f$ClassT\f$ is move assignable +/// \brief Check if \emph{ClassT} is move assignable /// \tparam ClassT The class type to test template struct is_move_assignable : bool_constant, add_rvalue_reference_t)> {}; @@ -1470,7 +1446,7 @@ template constexpr bool_t is_move_assignable_v = is_move_assign // fennec::is_trivially_move_assignable -------------------------------------------------------------------------------- /// -/// \brief Check if \f$ClassT\f$ is trivially_move assignable +/// \brief Check if \emph{ClassT} is trivially_move assignable /// \tparam ClassT The class type to test template struct is_trivially_move_assignable : bool_constant, add_rvalue_reference_t)> {}; @@ -1484,7 +1460,7 @@ template constexpr bool_t is_trivially_move_assignable_v = is_t // fennec::is_nothrow_move_assignable -------------------------------------------------------------------------------- /// -/// \brief Check if \f$ClassT\f$ is nothrow_move assignable +/// \brief Check if \emph{ClassT} is nothrow_move assignable /// \tparam ClassT The class type to test template struct is_nothrow_move_assignable : bool_constant, add_rvalue_reference_t)> {}; @@ -1498,7 +1474,7 @@ template constexpr bool_t is_nothrow_move_assignable_v = is_not // fennec::is_destructible --------------------------------------------------------------------------------------------- /// -/// \brief Check if \f$ClassT\f$ is destructible +/// \brief Check if \emph{ClassT} is destructible /// \tparam ClassT The class type to test template struct is_destructible : detail::_is_destructible::type {}; @@ -1512,10 +1488,14 @@ template constexpr bool_t is_destructible_v = is_destructible struct is_trivially_destructible +#if FENNEC_HAS_BUILTIN_IS_TRIVIALLY_DESTRUCTIBLE : bool_constant {}; +#else + : bool_constant {}; +#endif /// /// \brief Shorthand for `is_trivially_destructible::value` @@ -1526,7 +1506,7 @@ template constexpr bool_t is_trivially_destructible_v = is_triv // fennec::is_nothrow_destructible ------------------------------------------------------------------------------------- /// -/// \brief Check if \f$ClassT\f$ is nothrow destructible +/// \brief Check if \emph{ClassT} is nothrow destructible /// \tparam ClassT The class type to test template struct is_nothrow_destructible : detail::_is_nothrow_destructible::type {}; @@ -1547,7 +1527,7 @@ template constexpr bool_t is_nothrow_destructible_v = is_nothro /// /// \brief Check if the two types are identical /// -/// \details Checks if \f$T0\f$ and \f$T1\f$ are identical and store it in `is_same::value` +/// \details Checks if \emph{T0} and \emph{T1} are identical and store it in `is_same::value` /// \tparam T0 first type to check /// \tparam T1 second type to check template struct is_same : false_type {}; @@ -1556,7 +1536,7 @@ template struct is_same : false_type {}; template struct is_same : true_type {}; /// -/// \brief Shorthand for ```is_same::value``` +/// \brief Shorthand for `(.*?)` /// \tparam T0 first type to check /// \tparam T1 second type to check template constexpr bool_t is_same_v = is_same {}; @@ -1566,9 +1546,9 @@ template constexpr bool_t is_same_v = is_same // fennec::is_base_of -------------------------------------------------------------------------------------------------- /// -/// \brief Check if \f$Derived\f$ has a base type of \f$Base\f$ +/// \brief Check if \emph{Derived} has a base type of \emph{Base} /// -/// \details Checks if \f$Base\f$ is a base type of \f$Derived\f$ and stores it in `is_base_of::value` +/// \details Checks if \emph{Base} is a base type of \emph{Derived} and stores it in `is_base_of::value` /// \tparam Base base type to check /// \tparam Derived derived type to check template struct is_base_of : bool_constant< @@ -1576,7 +1556,7 @@ template struct is_base_of : bool_constant< > {}; /// -/// \brief Shorthand for ```is_base_of::value``` +/// \brief Shorthand for `(.*?)` /// \tparam Base base type to check /// \tparam Derived derived type to check template constexpr bool_t is_base_of_v = is_base_of {}; @@ -1586,9 +1566,9 @@ template constexpr bool_t is_base_of_v = is_bas // fennec::is_iterable ------------------------------------------------------------------------------------------------- /// -/// \brief Check if type \f$T\f$ is iterable +/// \brief Check if type \emph{T} is iterable /// -/// \details Checks if \f$T\f$ +/// \details Checks if \emph{Base} is iterable and stores it in `is_base_of::value` /// \tparam T type to check template struct is_iterable : decltype(detail::_is_iterable(0)) {}; @@ -1599,12 +1579,28 @@ template constexpr bool_t is_iterable_v = is_iterable{}; +// fennec::is_iterator ------------------------------------------------------------------------------------------------- + +/// +/// \brief Check if type \emph{T} is an iterator +/// +/// \details Checks if \emph{T} is an iterator and stores it in `is_base_of::value` +/// \tparam T type to check +template struct is_iterator : decltype(detail::_is_iterator(0)) {}; + +/// +/// \brief Shorthand for `is_iterator::value` +/// \tparam T type to check +template constexpr bool_t is_iterator_v = is_iterator{}; + + + // fennec::is_indexable ------------------------------------------------------------------------------------------------ /// -/// \brief Check if type \f$T\f$ is indexable +/// \brief Check if type \emph{T} is indexable /// -/// \details Checks if \f$T\f$ +/// \details Checks if \emph{T} /// \tparam T type to check template struct is_indexable : decltype(detail::_is_indexable(0)) {}; @@ -1618,9 +1614,9 @@ template constexpr bool_t is_indexable_v = is_indexable{}; // fennec::is_mappable ------------------------------------------------------------------------------------------------- /// -/// \brief Check if type \f$T\f$ is mappable +/// \brief Check if type \emph{T} is mappable /// -/// \details Checks if \f$T\f$ +/// \details Checks if \emph{T} /// \tparam T type to check template struct is_mappable : decltype(detail::_is_mappable(0)) {}; diff --git a/include/fennec/lang/type_transforms.h b/include/fennec/lang/type_transforms.h index 7442664..77a4af1 100644 --- a/include/fennec/lang/type_transforms.h +++ b/include/fennec/lang/type_transforms.h @@ -194,9 +194,9 @@ template using decay_t = typename decay::type; // Pointer Conversions ================================================================================================= /// -/// \brief adds a pointer level to \f$T\f$ +/// \brief adds a pointer level to \emph{T} /// -/// \details adds a pointer to the provided type such that \f$T\f$ becomes \f$T*\f$ +/// \details adds a pointer to the provided type such that \emph{T} becomes \emph{T*} /// \tparam T Resultant Type template struct add_pointer : detail::_add_pointer{}; @@ -206,9 +206,9 @@ template using add_pointer_t = typename add_pointer::type; /// -/// \brief removes a pointer level from \f$T\f$ +/// \brief removes a pointer level from \emph{T} /// -/// \details removes a pointer from the provided type such that \f$T*\f$ becomes \f$T\f$ +/// \details removes a pointer from the provided type such that \emph{T*} becomes \emph{T} /// \tparam T Resultant Type template struct remove_pointer : detail::_remove_pointer {}; @@ -218,9 +218,9 @@ template using remove_pointer_t = typename remove_pointer::type; /// -/// \brief removes all pointer levels from \f$T\f$ +/// \brief removes all pointer levels from \emph{T} /// -/// \details removes all pointers from the provided type such that \f$T*\f$, \f$T**\f$, etc. becomes \f$T\f$ +/// \details removes all pointers from the provided type such that \emph{T*}, \emph{T**}, etc. becomes \emph{T} /// \tparam T Resultant Type template struct strip_pointers : conditional_t< detail::_is_pointer::value, @@ -237,9 +237,9 @@ template using strip_pointers_t = strip_pointers::type; // Reference Conversions =============================================================================================== /// -/// \brief add a reference to \f$T\f$ +/// \brief add a reference to \emph{T} /// -/// \details adds a pointer to the provided type such that \f$T\f$ becomes \f$T\&\f$ +/// \details adds a pointer to the provided type such that \emph{T} becomes \emph{T\&} /// \tparam T Resultant Type template struct add_reference : type_identity {}; @@ -249,9 +249,9 @@ template using add_reference_t = typename add_reference::type; /// -/// \brief add a lvalue reference to \f$T\f$ +/// \brief add a lvalue reference to \emph{T} /// -/// \details adds a lvalue reference to the provided type such that \f$T\f$ becomes \f$T\&\f$ +/// \details adds a lvalue reference to the provided type such that \emph{T} becomes \emph{T\&} /// \tparam T Reference Type template struct add_lvalue_reference : detail::_add_lvalue_reference {}; @@ -261,9 +261,9 @@ template using add_lvalue_reference_t = typename add_lvalue_referen /// -/// \brief add a rvalue reference to \f$T\f$ +/// \brief add a rvalue reference to \emph{T} /// -/// \details adds a rvalue reference to the provided type such that \f$T\f$ becomes \f$T\&\&\f$ +/// \details adds a rvalue reference to the provided type such that \emph{T} becomes \emph{T\&\&} /// \tparam T Reference Type template struct add_rvalue_reference : detail::_add_rvalue_reference {}; @@ -273,9 +273,9 @@ template using add_rvalue_reference_t = typename add_rvalue_referen /// -/// \brief remove a reference from \f$T\f$ +/// \brief remove a reference from \emph{T} /// -/// \details removes references from the provided type such that \f$T\&\f$ and \f$T\&\&\f$ become \f$T\f$ +/// \details removes references from the provided type such that \emph{T\&} and \emph{T\&\&} become \emph{T} /// \tparam T Reference Type template struct remove_reference : type_identity {}; @@ -294,9 +294,9 @@ template using remove_reference_t = typename remove_reference::t // Const & Volatile Conversions ======================================================================================== /// -/// \brief add the const qualifier to the provided type \f$T\f$ +/// \brief add the const qualifier to the provided type \emph{T} /// -/// \details adds const qualification to the provided type such that \f$T\f$ becomes \f$const\quad T\f$ +/// \details adds const qualification to the provided type such that \emph{T} becomes \emph{const\quad T} /// \tparam T Reference Type template struct add_const : detail::_add_const {}; @@ -306,9 +306,9 @@ template using add_const_t = typename add_const::type; /// -/// \brief remove the const qualifier from the provided type \f$T\f$ +/// \brief remove the const qualifier from the provided type \emph{T} /// -/// \details removes const qualification from the provided type such that \f$const\quad T\f$ becomes \f$T\f$ +/// \details removes const qualification from the provided type such that \emph{const\quad T} becomes \emph{T} /// \tparam T Reference Type template struct remove_const : detail::_remove_const {}; @@ -319,9 +319,9 @@ template using remove_const_t = typename remove_const::type; /// -/// \brief add the volatile qualifier to the provided type \f$T\f$ +/// \brief add the volatile qualifier to the provided type \emph{T} /// -/// \details removes references from the provided type such that \f$T\f$ becomes \f$volatile\quad T\f$ +/// \details removes references from the provided type such that \emph{T} becomes \emph{volatile\quad T} /// \tparam T Reference Type template struct add_volatile : detail::_add_volatile {}; @@ -331,9 +331,9 @@ template using add_volatile_t = typename add_volatile::type; /// -/// \brief remove the volatile qualifier from the provided type \f$T\f$ +/// \brief remove the volatile qualifier from the provided type \emph{T} /// -/// \details removes references from the provided type such that \f$volatile\quad T\f$ becomes \f$T\f$ +/// \details removes references from the provided type such that \emph{volatile\quad T} becomes \emph{T} /// \tparam T Reference Type template struct remove_volatile : detail::_remove_volatile {}; @@ -344,10 +344,10 @@ template using remove_volatile_t = typename remove_volatile::type /// -/// \brief remove the volatile qualifier from the provided type \f$T\f$ +/// \brief remove the volatile qualifier from the provided type \emph{T} /// -/// \details removes references from the provided type such that \f$T\f$, \f$const\quad T\f$, and \f$volatile\quad T\f$ -/// become \f$const volatile T\f$ +/// \details removes references from the provided type such that \emph{T}, \emph{const\quad T}, and \emph{volatile\quad T} +/// become \emph{const volatile T} /// \tparam T Reference Type template struct add_cv : detail::_add_cv {}; @@ -358,10 +358,10 @@ template using add_cv_t = typename add_cv::type; /// -/// \brief remove the const and volatile qualifiers from the provided type \f$T\f$ +/// \brief remove the const and volatile qualifiers from the provided type \emph{T} /// -/// \details removes const and volatile from the provided type such that \f$const\quad T\f$, \f$volatile\quad T\f$, and -/// \f$const\quad volatile\quad T\f$ become \f$T\f$ +/// \details removes const and volatile from the provided type such that \emph{const\quad T}, \emph{volatile\quad T}, and +/// \emph{const\quad volatile\quad T} become \emph{T} /// \tparam T Reference Type template struct remove_cv : detail::_remove_cv {}; @@ -372,7 +372,7 @@ template using remove_cv_t = typename remove_cv::type; /// -/// \brief add a reference and the const volatile qualifiers from the provided type \f$T\f$ +/// \brief add a reference and the const volatile qualifiers from the provided type \emph{T} /// /// \details adds references and const volatile qualifiers to the provided type. /// \tparam T Reference Type @@ -385,7 +385,7 @@ template using add_cvref_t = typename add_cvref::type; /// -/// \brief removes references as well as the const and volatile qualifiers from the provided type \f$T\f$ +/// \brief removes references as well as the const and volatile qualifiers from the provided type \emph{T} /// /// \details removes const and volatile from the provided type such that /// \tparam T Reference Type @@ -399,7 +399,7 @@ template using remove_cvref_t = typename remove_cvref::type; /// -/// \brief removes references and pointers as well as the const and volatile qualifiers from the provided type \f$T\f$ +/// \brief removes references and pointers as well as the const and volatile qualifiers from the provided type \emph{T} /// /// \details removes const and volatile from the provided type such that /// \tparam T Reference Type diff --git a/include/fennec/lang/utility.h b/include/fennec/lang/utility.h index becf5f2..16a47cf 100644 --- a/include/fennec/lang/utility.h +++ b/include/fennec/lang/utility.h @@ -84,10 +84,10 @@ template constexpr T&& forward(remove_reference_t&& x) noexcept { #endif -/// \brief Copies \f$v\f$ to a new object of `decay_t` +/// \brief Copies \emph{v} to a new object of `decay_t` /// \tparam T The type /// \param v The object -/// \returns A stack allocated copy of \f$v\f$ in `decay_t` +/// \returns A stack allocated copy of \emph{v} in `decay_t` template constexpr decay_t decay_copy(T&& v) { return fennec::forward(v); } diff --git a/include/fennec/math/common.h b/include/fennec/math/common.h index 35d55df..2e8efa2 100644 --- a/include/fennec/math/common.h +++ b/include/fennec/math/common.h @@ -295,11 +295,11 @@ namespace fennec // Sign ================================================================================================================ /// -/// \brief Returns \f$1\f$ if \f$x > 0\f$, \f$0\f$ if \f$x = 0\f$, or \f$-1\f$ if \f$x<0\f$ +/// \brief Returns \math{1} if \math{x > 0}, \math{0} if \math{x = 0}, or \math{-1} if \math{x<0} /// -/// \returns \f$1\f$ if \f$x > 0\f$, \f$0\f$ if \f$x = 0\f$, or \f$-1\f$ if \f$x<0\f$

+/// \returns \math{1} if \math{x > 0}, \math{0} if \math{x = 0}, or \math{-1} if \math{x<0}

/// \details We can express this as,

-/// \f$\text{sign}(x) = \text{sgn}(x) = \left\{\begin{array}{lr} -1 & x < 0, \\ 0 & x = 0, \\ 1 & x > 0.\end{array}\right.\f$

+/// \math{\text{sign}(x) = \text{sgn}(x) = \left\{\begin{array}{lr} -1 & x < 0, \\ 0 & x = 0, \\ 1 & x > 0.\end{array}\right.}

/// /// \param x input value template @@ -311,11 +311,11 @@ constexpr genType sign(genType x) { // Absolute Value ====================================================================================================== /// -/// \brief Returns \f$x\f$ if \f$x \ge 0\f$, otherwise it returns \f$-x\f$ +/// \brief Returns \math{x} if \math{x \ge 0}, otherwise returns \math{-x} /// -/// \returns \f$x\f$ if \f$x \ge 0\f$, otherwise it returns \f$-x\f$.

+/// \returns \math{x} if \math{x \ge 0}, otherwise it returns \math{-x}.

/// \details We can express this as,

-/// \f$\text{abs}(x)=\left|x\right|\f$.

+/// \math{\text{abs}(x)=\left|x\right|}.

/// /// \param x input value template @@ -337,11 +337,11 @@ constexpr genType abs(genType x) { // Floor =============================================================================================================== /// -/// \brief Returns a value equal to the nearest integer that is less than or equal to \f$x\f$ +/// \brief Returns a value equal to the nearest integer that is less than or equal to \math{x} /// -/// \returns a value equal to the nearest integer that is less than or equal to \f$x\f$

+/// \returns a value equal to the nearest integer that is less than or equal to \math{x}

/// \details We can express this as,

-/// \f$\text{floor}(x)=\lfloor x\rfloor\f$

+/// \math{\text{floor}(x)=\lfloor x\rfloor}

/// /// \param x input value template @@ -354,11 +354,11 @@ constexpr genType floor(genType x) { // Ceil ================================================================================================================ /// -/// \brief Returns a value equal to the nearest integer that is greater than or equal to \f$x\f$ +/// \brief Returns a value equal to the nearest integer that is greater than or equal to \math{x} /// -/// \returns a value equal to the nearest integer that is greater than or equal to \f$x\f$

+/// \returns a value equal to the nearest integer that is greater than or equal to \math{x}

/// \details We can express this as,

-/// \f$\text{ceil}(x)=\lceil{x}\rceil\f$

+/// \math{\text{ceil}(x)=\lceil{x}\rceil}

/// /// \param x input value template @@ -371,12 +371,12 @@ constexpr genType ceil(genType x) { // Round =============================================================================================================== /// -/// \brief Returns a value equal to the nearest integer. In C++, a fractional part of \f$0.5\f$ will always round up. +/// \brief Returns a value equal to the nearest integer. In C++, a fractional part of \math{0.5} will always round up. /// /// \returns a value equal to the nearest integer.

-/// \details In C++, a fractional part of \f$0.5\f$ will always round up.

+/// \details In C++, a fractional part of \math{0.5} will always round up.

/// We can express this as,

-/// \f$\text{round}(x) = \text{sgn}(x) \cdot \lfloor \left| x \right| + 0.5 \rfloor\f$

+/// \math{\text{round}(x) = \text{sgn}(x) \cdot \lfloor \left| x \right| + 0.5 \rfloor}

/// /// \param x input value template constexpr genType round(genType x) { @@ -388,11 +388,11 @@ template constexpr genType round(genType x) { // Trunc =============================================================================================================== /// -/// \brief Returns a value equal to the nearest integer that is less than or equal to \f$x\f$ +/// \brief Returns a value equal to the nearest integer that is less than or equal to \math{x} /// -/// \returns a value equal to the nearest integer that is less than or equal to \f$x\f$

+/// \returns a value equal to the nearest integer that is less than or equal to \math{x}

/// \details We can express this as,

-/// \f$\text{trunc}(x) = \text{sgn}(x) \cdot \lceil \left| x \right| - 0.5 \rceil\f$

+/// \math{\text{trunc}(x) = \text{sgn}(x) \cdot \lceil \left| x \right| - 0.5 \rceil}

/// /// \param x input value template @@ -405,13 +405,13 @@ constexpr genType trunc(genType x) { // Round Even ========================================================================================================== /// -/// \brief Returns a value equal to the nearest integer. In C++, a fractional part of \f$0.5\f$ will always +/// \brief Returns a value equal to the nearest integer. In C++, a fractional part of \math{0.5} will always /// round to the nearest even integer. /// /// \returns a value equal to the nearest integer.

-/// \details In C++, a fractional part of \f$0.5\f$ will always round to the nearest even integer.

+/// \details In C++, a fractional part of \math{0.5} will always round to the nearest even integer.

/// We can express this as,

-/// \f$\text{roundEven}() = \begin{cases}\lfloor{x}\rfloor + \text{mod}(\lfloor{x}\rfloor, 2.0) & \text{fract}(x) = 0.5, \\ \text{round}(x) \end{cases}\f$

+/// \math{\text{roundEven}() = \begin{cases}\lfloor{x}\rfloor + \text{mod}(\lfloor{x}\rfloor, 2.0) & \text{fract}(x) = 0.5, \\ \text{round}(x) \end{cases}}

/// /// \param x input value template @@ -451,11 +451,11 @@ constexpr genType roundEven(genType x) { // Fract =============================================================================================================== /// -/// \brief Returns \f$x - floor(x)\f$ +/// \brief Returns \math{x - floor(x)} /// -/// \returns \f$x - \text{floor}(x)\f$

+/// \returns \math{x - \text{floor}(x)}

/// \details We can express this as,

-/// \f$\text{fract}(x)=x-\text{floor}\f$

+/// \math{\text{fract}(x)=x-\text{floor}}

/// /// \param x input value template @@ -467,11 +467,11 @@ constexpr genType fract(genType x) { // Mod ================================================================================================================= /// -/// \brief Modulus. Returns \f$x-y\cdot floor (x/y)\f$ +/// \brief Modulus. Returns \math{x-y\cdot floor (x/y)} /// -/// \returns \f$x-y\cdot\text{floor}(x/y)\f$

+/// \returns \math{x-y\cdot\text{floor}(x/y)}

/// \details We can express this as,

-/// \f$\text{fract}(x)=x-\text{floor}(\frac{x}{y})\f$

+/// \math{\text{fract}(x)=x-\text{floor}(\frac{x}{y})}

/// /// \param x dividend /// \param y divisor @@ -484,11 +484,11 @@ constexpr genType mod(genType x, genType y) { // ModF ================================================================================================================ /// -/// \brief Returns the fractional part of \f$x\f$ and stores the integral part in \f$i\f$. +/// \brief Returns the fractional part of \math{x} and stores the integral part in \math{i}. /// -/// \returns the fractional part of \f$x\f$ and stores the integral part in \f$i\f$.

+/// \returns the fractional part of \math{x} and stores the integral part in \math{i}.

/// \details We can express this as,

-/// \f$\text{modf}(x) = \text{trunc}(x),\, i := \text{fract}(x)\f$

+/// \math{\text{modf}(x) = \text{trunc}(x),\, i := \text{fract}(x)}

/// /// \param x input value /// \param i integral out @@ -501,14 +501,14 @@ constexpr genType modf(genType x, genType& i) { // Is NaN ============================================================================================================== /// -/// \brief Returns **true** if \f$x\f$ holds a NaN. Returns **false** otherwise. +/// \brief Returns **true** if \math{x} holds a NaN. Returns **false** otherwise. /// -/// \returns **true** if \f$x\f$ holds a NaN. Returns **false** otherwise.

-/// \details \f$NaN\f$ is a concept unique to computing. It strictly means, and more specifically, +/// \returns **true** if \math{x} holds a NaN. Returns **false** otherwise.

+/// \details \math{NaN} is a concept unique to computing. It strictly means, and more specifically, /// floating point values can only represent *real* numbers. This is why some functions, -/// like \ref fennec::sqrt "sqrt()", return \f$NaN\f$ when an expression would return -/// a value in a different coordinate space. There are other cases, such as \f$\frac{1}{x}\f$, -/// where \f$x=0\f$ is undefined, and respectively the return value is also \f$NaN\f$.

+/// like \ref fennec::sqrt "sqrt()", return \math{NaN} when an expression would return +/// a value in a different coordinate space. There are other cases, such as \math{\frac{1}{x}}, +/// where \math{x=0} is undefined, and respectively the return value is also \math{NaN}.

/// /// To learn more, see [IEEE 754](https://en.wikipedia.org/wiki/IEEE_754)

/// @@ -522,10 +522,10 @@ constexpr genBType isnan(genType x) { // Is Inf ============================================================================================================== /// -/// \brief Returns **true** if \f$x\f$ holds a positive or negative infinity. Returns **false** otherwise.

+/// \brief Returns **true** if \math{x} holds a positive or negative infinity. Returns **false** otherwise.

/// -/// \returns **true** if \f$x\f$ holds a positive or negative infinity. Returns **false** otherwise. -/// \details \f$\inf\f$, or \f$\infty\f$, is used to express any function that is boundless, endless, or larger +/// \returns **true** if \math{x} holds a positive or negative infinity. Returns **false** otherwise. +/// \details \math{\inf}, or \math{\infty}, is used to express any function that is boundless, endless, or larger /// than any natural number. This function has applications in Set Theory and Mathematical Analysis.

/// /// \param x input value @@ -553,13 +553,13 @@ constexpr genIType floatBitsToInt(genType x) { /// \returns a signed or unsigned integer value representing the encoding of a floating-point value. /// The float value's bit-level representation is preserved.

/// \details we can express this in set theory, i.e.

-/// let \f$B\f$ be a set, such that, \f$B=\left\lbrace{b_{0},...b_{32}}\right\rbrace\f$ and \f$b_{i} \in S\f$ where \f$S=\left\lbrace{0, 1}\right\rbrace\f$
-/// let \f$m_B=\frac{b_{0}}{2^1}+\cdots +\frac{b_{i}}{2^{i+1}}+\cdots +\frac{b_{22}}{2^{23}}\begin{cases}1&\end{cases}\f$
-/// let \f$p_B=b_{23}\cdot 2^0+\cdots +b_i\cdot 2^{i-23}+\cdots +b_{30}\cdot 2^7-127\f$
-/// let \f$s_B=\begin{cases}-1,&b_{31}=1 \\ 1\end{cases}\f$

-/// then, \f$x_B=s_B m_B 2^{p_B}\f$
-/// and, \f$i_B=-b_{31} 2^{31}+\sum_{i=0}^{30}{a_i 2^i}\f$
-/// and, \f$u_B=\sum_{i=0}^{31}{a_i 2^i}\f$

+/// let \math{B} be a set, such that, \math{B=\left\lbrace{b_{0},...b_{32}}\right\rbrace} and \math{b_{i} \in S} where \math{S=\left\lbrace{0, 1}\right\rbrace}
+/// let \math{m_B=\frac{b_{0}}{2^1}+\cdots +\frac{b_{i}}{2^{i+1}}+\cdots +\frac{b_{22}}{2^{23}}\begin{cases}1&\end{cases}}
+/// let \math{p_B=b_{23}\cdot 2^0+\cdots +b_i\cdot 2^{i-23}+\cdots +b_{30}\cdot 2^7-127}
+/// let \math{s_B=\begin{cases}-1,&b_{31}=1 \\ 1\end{cases}}

+/// then, \math{x_B=s_B m_B 2^{p_B}}
+/// and, \math{i_B=-b_{31} 2^{31}+\sum_{i=0}^{30}{a_i 2^i}}
+/// and, \math{u_B=\sum_{i=0}^{31}{a_i 2^i}}

/// /// \param x value to convert template requires(is_floating_point_v and is_integral_v and is_unsigned_v and sizeof(genType) == sizeof(genUType)) @@ -581,13 +581,13 @@ constexpr genType intBitsToFloat(genIType x) { /// /// \returns a floating-point value corresponding to a signed or unsigned integer encoding of a floating-point value.

/// \details we can express this in set theory, i.e.

-/// let \f$B\f$ be a set, such that, \f$B=\left\lbrace{b_{0},...b_{32}}\right\rbrace\f$ and \f$b_{i} \in S\f$ where \f$S=\left\lbrace{0, 1}\right\rbrace\f$
-/// let \f$m_B=\frac{b_{0}}{2^1}+\cdots +\frac{b_{i}}{2^{i+1}}+\cdots +\frac{b_{22}}{2^{23}}\begin{cases}1&\end{cases}\f$
-/// let \f$p_B=b_{23}\cdot 2^0+\cdots +b_i\cdot 2^{i-23}+\cdots +b_{30}\cdot 2^7-127\f$
-/// let \f$s_B=\begin{cases}-1,&b_{31}=1 \\ 1\end{cases}\f$

-/// then, \f$x_B=s_B m_B 2^{p_B}\f$
-/// and, \f$i_B=-b_{31} 2^31+\sum_{i=0}^{30}{a_i 2^i}\f$
-/// and, \f$u_B=\sum_{i=0}^{31}{a_i 2^i}\f$

+/// let \math{B} be a set, such that, \math{B=\left\lbrace{b_{0},...b_{32}}\right\rbrace} and \math{b_{i} \in S} where \math{S=\left\lbrace{0, 1}\right\rbrace}
+/// let \math{m_B=\frac{b_{0}}{2^1}+\cdots +\frac{b_{i}}{2^{i+1}}+\cdots +\frac{b_{22}}{2^{23}}\begin{cases}1&\end{cases}}
+/// let \math{p_B=b_{23}\cdot 2^0+\cdots +b_i\cdot 2^{i-23}+\cdots +b_{30}\cdot 2^7-127}
+/// let \math{s_B=\begin{cases}-1,&b_{31}=1 \\ 1\end{cases}}

+/// then, \math{x_B=s_B m_B 2^{p_B}}
+/// and, \math{i_B=-b_{31} 2^31+\sum_{i=0}^{30}{a_i 2^i}}
+/// and, \math{u_B=\sum_{i=0}^{31}{a_i 2^i}}

/// /// \param x value to convert template requires(is_floating_point_v and is_integral_v and is_unsigned_v and sizeof(genType) == sizeof(genUType)) @@ -600,9 +600,9 @@ constexpr genType uintBitsToFloat(genUType x) { // fma ================================================================================================================= /// -/// \brief Computes and returns \f$a \cdot b + c\f$.

+/// \brief Computes and returns \math{a \cdot b + c}.

/// -/// \returns \f$a \cdot b + c\f$. +/// \returns \math{a \cdot b + c}. /// \details In C++, this function will use the [fused multiply-add](https://en.wikipedia.org/wiki/Multiply%E2%80%93accumulate_operation), /// when the instruction is present on the target architecture.

/// @@ -619,16 +619,16 @@ constexpr genType fma(genType a, genType b, genType c) { // frexp =============================================================================================================== /// -/// \brief Splits \f$x\f$ into a floating-point significand in the range \f$[0.5,1.0]\f$, and an integral exponent of two, -/// such that \f$x=sig \cdot 2^{exp}\f$. +/// \brief Splits \math{x} into a floating-point significand in the range \math{[0.5,1.0]}, and an integral exponent of two, +/// such that \math{x=sig \cdot 2^{exp}}. /// /// \returns The significand of the expression.

-/// \details The significand is returned by the function and the exponent is returned in the parameter \f$exp\f$. +/// \details The significand is returned by the function and the exponent is returned in the parameter \math{exp}. /// For a floating-point value of zero, the significand and exponent are both zero. If an implementation /// supports signed zero, an input value of minus zero should return a significand of minus zero. For a /// floating-point value that is an infinity or is not a number, the results are undefined. If the input -/// \f$x\f$ is a vector, this operation is performed in a component-wise manner; the value returned by the -/// function and the value written to \f$exp\f$ are vectors with the same number of components as \f$x\f$.

+/// \math{x} is a vector, this operation is performed in a component-wise manner; the value returned by the +/// function and the value written to \math{exp} are vectors with the same number of components as \math{x}.

/// /// \param x The floating-point value to split /// \param exp The variable to store the exponent in @@ -642,11 +642,11 @@ constexpr genType frexp(genType x, genIType& exp) { // ldexp =============================================================================================================== /// -/// \brief Builds a floating-point number from \f$x\f$ and the corresponding integral exponent of two in \f$exp\f$ +/// \brief Builds a floating-point number from \math{x} and the corresponding integral exponent of two in \math{exp} /// -/// \returns \f${x}\cdot{2^{exp}}\f$ +/// \returns \math{{x}\cdot{2^{exp}}} /// \details Builds a floating-point number from x and the corresponding integral exponent of two in exp, -/// returning: \f${x}\cdot{2^{exp}}\f$. If this product is too large to be represented in the floating-point +/// returning: \math{{x}\cdot{2^{exp}}}. If this product is too large to be represented in the floating-point /// type, the result is undefined. If exp is greater than +128 (single-precision) or +1024 (double-precision), /// the value returned is undefined. If exp is less than -126 (single-precision) or -1022 (double-precision), /// the value returned may be flushed to zero. Additionally, splitting the value into a significand and @@ -676,14 +676,14 @@ constexpr genType ldexp(genType x, genIType exp) { // Min ================================================================================================================= /// -/// \brief Returns \f$y\f$ if \f$x
+/// \returns \math{y} if \math{x
/// \details We can express this as,

-/// \f$\text{min}(x, y)=\begin{cases}y, & y < x \\ x\end{cases}\f$

+/// \math{\text{min}(x, y)=\begin{cases}y, & y < x \\ x\end{cases}}

/// -/// \param x input value \f$x\f$ -/// \param y input value \f$y\f$ +/// \param x input value \math{x} +/// \param y input value \math{y} template constexpr genType min(genType x, genType y) { return (y < x) ? y : x; @@ -693,11 +693,11 @@ constexpr genType min(genType x, genType y) { // Max ================================================================================================================= /// -/// \brief Returns \f$y\f$ if \f$y
+/// \returns \math{y} if \math{y
/// \details We can express this as,

-/// \f$\text{max}(x, y)=\begin{cases}y, & x < y \\ x\end{cases}\f$

+/// \math{\text{max}(x, y)=\begin{cases}y, & x < y \\ x\end{cases}}

/// /// \param x first input value /// \param y second input value @@ -710,11 +710,11 @@ constexpr genType max(genType x, genType y) { // Clamp =============================================================================================================== /// -/// \brief Returns \f$min (max (x, minVal), maxVal)\f$ +/// \brief Returns \math{min (max (x, minVal), maxVal)} /// -/// \returns \f$\text{min}(\text{max}(x, minVal), maxVal)\f$. Results are undefined if \f$minVal > maxVal\f$

+/// \returns \math{\text{min}(\text{max}(x, minVal), maxVal)}. Results are undefined if \math{minVal > maxVal}

/// \details We can express this as,

-/// \f$\text{clamp}(x, min, max)=\begin{cases}min, & x < min \\ x \\ max, & x > max\end{cases}\f$

+/// \math{\text{clamp}(x, min, max)=\begin{cases}min, & x < min \\ x \\ max, & x > max\end{cases}}

/// /// \param x input value /// \param minVal minimum value @@ -738,13 +738,13 @@ constexpr genType clamp(genType x, genType minVal, genType maxVal) { // Step ================================================================================================================ /// -/// \brief Returns \f$0.0\f$ if \f$x
+/// \returns \math{0.0} if \math{x
/// \details We can express this as,

-/// \f$\text{step}(edge, x)=\begin{cases}0.0 & x < edge \\ 1.0 \end{cases}\f$

+/// \math{\text{step}(edge, x)=\begin{cases}0.0 & x < edge \\ 1.0 \end{cases}}

/// -/// \param edge The \f$x\f$ coordinate of the discontinuity +/// \param edge The \math{x} coordinate of the discontinuity /// \param x The coordinate of the sample location template requires(is_floating_point_v) constexpr genType step(genType edge, genType x) { @@ -755,11 +755,11 @@ constexpr genType step(genType edge, genType x) { // Smoothstep ========================================================================================================== /// -/// \brief Returns \f$0.0\f$ if \f$x\le edge0\f$ and \f$1.0\f$ if \f$x\ge edge1\f$, and performs smooth Hermite -/// interpolation between \f$0\f$ and \f$1\f$ when \f$edge0
+/// \returns \math{0.0} if \math{x\le edge0} and \math{1.0} if \math{x\ge edge1}, and performs smooth Hermite +/// interpolation between \math{0} and \math{1} when \math{edge0
/// \details This is useful in cases where you would want a threshold function with a smooth transition.

/// This is equivalent to:

/// \code{.glsl} @@ -767,13 +767,13 @@ constexpr genType step(genType edge, genType x) { /// t = clamp((x - edge0) / (edge1 - edge0), 0, 1); /// return t * t * (3 - 2 * t); /// \endcode
-/// Results are undefined if \f$edge0\ge edge1\f$.

+/// Results are undefined if \math{edge0\ge edge1}.

/// We can express this as,

-/// \f$\text{smoothstep}(e_0, e_1, x)=\begin{cases}0, & {x}\le{e_0} \\ 3{\frac{x-e_0}{e_1-e_0}}^{2} - 2{\frac{x-e_0}{e_1-e_0}}^{3}, & {e_0}\le{x}\le{e_1} \\ 1, & {1}\le{e_x}\end{cases}\f$

+/// \math{\text{smoothstep}(e_0, e_1, x)=\begin{cases}0, & {x}\le{e_0} \\ 3{\frac{x-e_0}{e_1-e_0}}^{2} - 2{\frac{x-e_0}{e_1-e_0}}^{3}, & {e_0}\le{x}\le{e_1} \\ 1, & {1}\le{e_x}\end{cases}}

/// -/// \param edge0 \f$x\f$ value where the function returns \f$0.0\f$ -/// \param edge1 \f$x\f$ value where the function returns \f$1.0\f$ -/// \param x \f$x\f$ coordinate input +/// \param edge0 \math{x} value where the function returns \math{0.0} +/// \param edge1 \math{x} value where the function returns \math{1.0} +/// \param x \math{x} coordinate input template requires(is_floating_point_v) constexpr genType smoothstep(genType edge0, genType edge1, genType x) { genType t = fennec::clamp((x - edge0) / (edge1 - edge0), 0.0f, 1.0f); return t * t * (3 - 2 * t); @@ -783,13 +783,13 @@ constexpr genType smoothstep(genType edge0, genType edge1, genType x) { // Mix ================================================================================================================= /// -/// \brief Returns the linear blend of \f$x\f$ and \f$y\f$, i.e., \f$x \cdot (1-a) + y \cdot a\f$ +/// \brief Returns the linear blend of \math{x} and \math{y}, i.e., \math{x \cdot (1-a) + y \cdot a} /// -/// \returns the linear blend of \f$x\f$ and \f$y\f$, i.e., \f$x \cdot (1-a) + y \cdot a\f$

+/// \returns the linear blend of \math{x} and \math{y}, i.e., \math{x \cdot (1-a) + y \cdot a}

/// \details We can express this as,

-/// \f$\text{mix}(x, y, a)=x+a \cdot (y - x)\f$

+/// \math{\text{mix}(x, y, a)=x+a \cdot (y - x)}

/// The reason for the difference between the mathematical definition and the glsl definition is -/// due to floating-point precision errors. Multiplying \f$x\f$ and \f$y\f$ separately preserves +/// due to floating-point precision errors. Multiplying \math{x} and \math{y} separately preserves /// their precision before the addition happens. /// /// \param x First value @@ -806,14 +806,14 @@ constexpr genType mix(genType x, genType y, genType a) { /// /// \brief Selects which value to return. For Vectors, when the boolean is a scalar, it selects the vector, otherwise, each component is selected. /// -/// \returns \f$x\f$ when \f$a=T\f$, otherwise returns \f$y\f$ +/// \returns \math{x} when \math{a=T}, otherwise returns \math{y} /// \details Selects which value to return. For Vectors, when the boolean is a scalar, /// it selects the vector, otherwise, each component is selected.

/// This implementation uses the ternary operator:
/// \code{.cpp}return a ? x : y;\endcode /// Which will get reduced down to a conditional move instruction over branching.

/// We can express this as,

-/// \f$\text{mix}(x, y, A) = \begin{cases} x, & A=T \\ y & A=F \end{cases}\f$

+/// \math{\text{mix}(x, y, A) = \begin{cases} x, & A=T \\ y & A=F \end{cases}}

/// /// \param x True Value /// \param y False Value diff --git a/include/fennec/math/detail/_math.h b/include/fennec/math/detail/_math.h index 8a69179..663747c 100644 --- a/include/fennec/math/detail/_math.h +++ b/include/fennec/math/detail/_math.h @@ -19,10 +19,37 @@ #ifndef FENNEC_MATH_DETAIL_MATH_H #define FENNEC_MATH_DETAIL_MATH_H + +// Handle including C math.h +// Unfortunately, each compiler needs its own if case in the macro chain below + +#if FENNEC_COMPILER_CLANG // Clang + +// Temporarily disable macro redefinition warning +#pragma clang diagnostic push +#pragma clang diagnostic ignored "-Wbuiltin-macro-redefined" + +// Undefine __cpluscplus macro to force using the C header #pragma push_macro("__cplusplus") #undef __cplusplus + +// Include math.h #include + +// Restore __cpluscplus definition and macro redefinition warning #pragma pop_macro("__cplusplus") +#pragma clang diagnostic pop + + +#elif FENNEC_COMPILER_GCC // GCC + +// This definition tells GCC to just use the C header, thanks GCC!!! +#ifndef _GLIBCXX_INCLUDE_NEXT_C_HEADERS +#define _GLIBCXX_INCLUDE_NEXT_C_HEADERS +#endif + +#include +#endif #undef div #undef acos diff --git a/include/fennec/math/exponential.h b/include/fennec/math/exponential.h index 57ecd98..b7d7fbe 100644 --- a/include/fennec/math/exponential.h +++ b/include/fennec/math/exponential.h @@ -97,10 +97,10 @@ namespace fennec // pow ================================================================================================================= /// -/// \brief Returns \f$x\f$ raised to the \f$y\f$ power, i.e., \f$x^y\f$. +/// \brief Returns \math{x} raised to the \math{y} power, i.e., \math{x^y}. /// -/// \returns \f$x\f$ raised to the \f$y\f$ power, i.e., \f$x^y\f$.

-/// \details Results are undefined if \f$x<0\f$.

Results are undefined if \f$x=0\f$ and \f${y}\le{0}\f$.

+/// \returns \math{x} raised to the \math{y} power, i.e., \math{x^y}.

+/// \details Results are undefined if \math{x<0}.

Results are undefined if \math{x=0} and \math{{y}\le{0}}.

/// /// \param x the base /// \param y the exponent @@ -113,9 +113,9 @@ constexpr genType pow(genType x, genType y) { // exp ================================================================================================================= /// -/// \brief Returns the natural exponentiation of \f$x\f$, i.e., \f$e^x\f$ +/// \brief Returns the natural exponentiation of \math{x}, i.e., \math{e^x} /// -/// \returns the natural exponentiation of \f$x\f$, i.e., \f$e^x\f$.

+/// \returns the natural exponentiation of \math{x}, i.e., \math{e^x}.

/// /// \param x the exponent template @@ -127,9 +127,9 @@ constexpr genType exp(genType x) { // exp2 ================================================================================================================ /// -/// \brief Returns 2 raised to the \f$x\f$ power, i.e., \f$e^x\f$ +/// \brief Returns 2 raised to the \math{x} power, i.e., \math{e^x} /// -/// \returns 2 raised to the \f$x\f$ power, i.e., \f$e^x\f$

+/// \returns 2 raised to the \math{x} power, i.e., \math{e^x}

/// /// \param x the exponent template constexpr genType exp2(genType x) { @@ -140,10 +140,10 @@ template constexpr genType exp2(genType x) { // log ================================================================================================================= /// -/// \brief Returns the natural logarithm of \f$x\f$. +/// \brief Returns the natural logarithm of \math{x}. /// -/// \returns the natural logarithm of \f$x\f$, i.e., returns the value \f$y\f$ which satisfies the equation \f$x=e^y\f$.

-/// \details Results are undefined if \f${x}\le{0}\f$.

+/// \returns the natural logarithm of \math{x}, i.e., returns the value \math{y} which satisfies the equation \math{x=e^y}.

+/// \details Results are undefined if \math{{x}\le{0}}.

/// /// \param x the input value template constexpr genType log(genType x) { @@ -154,11 +154,11 @@ template constexpr genType log(genType x) { // log2 ================================================================================================================ /// -/// \brief Returns the base 2 logarithm of \f$x\f$. +/// \brief Returns the base 2 logarithm of \math{x}. /// -/// \returns the base 2 logarithm of \f$x\f$, i.e., returns the value \f$y\f$ which satisfies the equation -/// \f$x=2^y\f$.

-/// \details Results are undefined if \f${x}\le{0}\f$.

+/// \returns the base 2 logarithm of \math{x}, i.e., returns the value \math{y} which satisfies the equation +/// \math{x=2^y}.

+/// \details Results are undefined if \math{{x}\le{0}}.

/// /// \param x the input value template constexpr genType log2(genType x) { @@ -169,10 +169,10 @@ template constexpr genType log2(genType x) { // sqrt ================================================================================================================ /// -/// \brief Returns \f$\sqrt{x}\f$. +/// \brief Returns \math{\sqrt{x}}. /// -/// \returns \f$\sqrt{x}\f$.

-/// \details Results are undefined if \f$x<0\f$

+/// \returns \math{\sqrt{x}}.

+/// \details Results are undefined if \math{x<0}

/// /// \param x the input value template constexpr genType sqrt(genType x) { @@ -183,10 +183,10 @@ template constexpr genType sqrt(genType x) { // inversesqrt ========================================================================================================= /// -/// \brief Returns \f$\frac{1}{\sqrt{x}}\f$. +/// \brief Returns \math{\frac{1}{\sqrt{x}}}. /// -/// \returns \f$\frac{1}{\sqrt{x}}\f$.

-/// \details Results are undefined if \f$x<0\f$.

+/// \returns \math{\frac{1}{\sqrt{x}}}.

+/// \details Results are undefined if \math{x<0}.

/// /// \param x the input value template constexpr genType inversesqrt(genType x) { diff --git a/include/fennec/math/ext/constants.h b/include/fennec/math/ext/constants.h index cb99ff2..2858c6d 100644 --- a/include/fennec/math/ext/constants.h +++ b/include/fennec/math/ext/constants.h @@ -546,148 +546,148 @@ namespace fennec // Rational Constants ================================================================================================== -template constexpr genType zero() { return genType(0); } //!< \returns The value of \f$0\f$ -template constexpr genType one() { return genType(1); } //!< \returns The value of \f$1\f$ -template constexpr genType one_half() { return genType(0.5); } //!< \returns The value of \f$\frac{1}{2}\f$ -template constexpr genType three_over_two() { return genType(1.5); } //!< \returns The value of \f$\frac{3}{2}\f$ +template constexpr genType zero() { return genType(0); } //!< \returns The value of \math{0} +template constexpr genType one() { return genType(1); } //!< \returns The value of \math{1} +template constexpr genType one_half() { return genType(0.5); } //!< \returns The value of \math{\frac{1}{2}} +template constexpr genType three_over_two() { return genType(1.5); } //!< \returns The value of \math{\frac{3}{2}} // Irrational Constants ================================================================================================ -template constexpr genType one_third() { return 0.33333333333333333333333333333333333333333333333333; } //!< \returns The value of \f$\frac{1}{3}\f$ with the highest precision for \f$genType\f$ -template constexpr genType two_thirds() { return 0.66666666666666666666666666666666666666666666666666; } //!< \returns The value of \f$\frac{2}{3}\f$ with the highest precision for \f$genType\f$ -template constexpr genType sqrt_two() { return 1.41421356237309504880168872420969807856967187537694; } //!< \returns The value of \f$\sqrt{2}\f$ with the highest precision for \f$genType\f$ -template constexpr genType sqrt_three() { return 1.73205080756887729352744634150587236694280525381038; } //!< \returns The value of \f$\sqrt{3}\f$ with the highest precision for \f$genType\f$ -template constexpr genType sqrt_five() { return 2.23606797749978969640917366873127623544061835961152; } //!< \returns The value of \f$\sqrt{5}\f$ with the highest precision for \f$genType\f$ -template constexpr genType sqrt_seven() { return 2.64575131106459059050161575363926042571025918308245; } //!< \returns The value of \f$\sqrt{7}\f$ with the highest precision for \f$genType\f$ -template constexpr genType sqrt_ten() { return 3.16227766016837933199889354443271853371955513932521; } //!< \returns The value of \f$\sqrt{10}\f$ with the highest precision for \f$genType\f$ -template constexpr genType one_over_sqrt_two() { return 0.70710678118654752440084436210484903928483593768847; } //!< \returns The value of \f$\frac{1}{\sqrt{2}}\f$ with the highest precision for \f$genType\f$ -template constexpr genType one_over_sqrt_three() { return 0.57735026918962576450914878050195745564760175127012; } //!< \returns The value of \f$\frac{1}{\sqrt{3}}\f$ with the highest precision for \f$genType\f$ -template constexpr genType one_over_sqrt_five() { return 0.44721359549995793928183473374625524708812367192230; } //!< \returns The value of \f$\frac{1}{\sqrt{5}}\f$ with the highest precision for \f$genType\f$ -template constexpr genType cbrt_two() { return 1.25992104989487316476721060727822835057025146470150; } //!< \returns The value of \f$\sqrt[3]{2}\f$ with the highest precision for \f$genType\f$ -template constexpr genType qdrt_two() { return 1.18920711500272106671749997056047591529297209246381; } //!< \returns The value of \f$\sqrt[4]{2}\f$ with the highest precision for \f$genType\f$ -template constexpr genType two_raised_sqrt_two() { return 2.66514414269022518865029724987313984827421131371465; } //!< \returns The value of \f${2}^{\sqrt{2}}\f$ with the highest precision for \f$genType\f$ +template constexpr genType one_third() { return 0.33333333333333333333333333333333333333333333333333; } //!< \returns The value of \math{\frac{1}{3}} with the highest precision for \emph{genType} +template constexpr genType two_thirds() { return 0.66666666666666666666666666666666666666666666666666; } //!< \returns The value of \math{\frac{2}{3}} with the highest precision for \emph{genType} +template constexpr genType sqrt_two() { return 1.41421356237309504880168872420969807856967187537694; } //!< \returns The value of \math{\sqrt{2}} with the highest precision for \emph{genType} +template constexpr genType sqrt_three() { return 1.73205080756887729352744634150587236694280525381038; } //!< \returns The value of \math{\sqrt{3}} with the highest precision for \emph{genType} +template constexpr genType sqrt_five() { return 2.23606797749978969640917366873127623544061835961152; } //!< \returns The value of \math{\sqrt{5}} with the highest precision for \emph{genType} +template constexpr genType sqrt_seven() { return 2.64575131106459059050161575363926042571025918308245; } //!< \returns The value of \math{\sqrt{7}} with the highest precision for \emph{genType} +template constexpr genType sqrt_ten() { return 3.16227766016837933199889354443271853371955513932521; } //!< \returns The value of \math{\sqrt{10}} with the highest precision for \emph{genType} +template constexpr genType one_over_sqrt_two() { return 0.70710678118654752440084436210484903928483593768847; } //!< \returns The value of \math{\frac{1}{\sqrt{2}}} with the highest precision for \emph{genType} +template constexpr genType one_over_sqrt_three() { return 0.57735026918962576450914878050195745564760175127012; } //!< \returns The value of \math{\frac{1}{\sqrt{3}}} with the highest precision for \emph{genType} +template constexpr genType one_over_sqrt_five() { return 0.44721359549995793928183473374625524708812367192230; } //!< \returns The value of \math{\frac{1}{\sqrt{5}}} with the highest precision for \emph{genType} +template constexpr genType cbrt_two() { return 1.25992104989487316476721060727822835057025146470150; } //!< \returns The value of \math{\sqrt[3]{2}} with the highest precision for \emph{genType} +template constexpr genType qdrt_two() { return 1.18920711500272106671749997056047591529297209246381; } //!< \returns The value of \math{\sqrt[4]{2}} with the highest precision for \emph{genType} +template constexpr genType two_raised_sqrt_two() { return 2.66514414269022518865029724987313984827421131371465; } //!< \returns The value of \math{{2}^{\sqrt{2}}} with the highest precision for \emph{genType} // Pi ================================================================================================================== // Pi & Tau -template constexpr genType pi() { return 3.14159265358979323846264338327950288419716939937510; } //!< \returns The value of \f$\pi\f$ with the highest precision for \f$genType\f$ -template constexpr genType tau() { return 6.28318530717958647692528676655900576839433879875021; } //!< \returns The value of \f$\tau\f$ with the highest precision for \f$genType\f$ +template constexpr genType pi() { return 3.14159265358979323846264338327950288419716939937510; } //!< \returns The value of \math{\pi} with the highest precision for \emph{genType} +template constexpr genType tau() { return 6.28318530717958647692528676655900576839433879875021; } //!< \returns The value of \math{\tau} with the highest precision for \emph{genType} // Multiples of Pi -template constexpr genType two_pi() { return 6.28318530717958647692528676655900576839433879875021; } //!< \returns The value of \f$2\pi\f$ with the highest precision for \f$genType\f$ -template constexpr genType three_pi() { return 9.42477796076937971538793014983850865259150819812531; } //!< \returns The value of \f$3\pi\f$ with the highest precision for \f$genType\f$ -template constexpr genType four_pi() { return 12.56637061435917295385057353311801153678867759750042; } //!< \returns The value of \f$4\pi\f$ with the highest precision for \f$genType\f$ +template constexpr genType two_pi() { return 6.28318530717958647692528676655900576839433879875021; } //!< \returns The value of \math{2\pi} with the highest precision for \emph{genType} +template constexpr genType three_pi() { return 9.42477796076937971538793014983850865259150819812531; } //!< \returns The value of \math{3\pi} with the highest precision for \emph{genType} +template constexpr genType four_pi() { return 12.56637061435917295385057353311801153678867759750042; } //!< \returns The value of \math{4\pi} with the highest precision for \emph{genType} // Fractions of Pi -template constexpr genType half_pi() { return 1.57079632679489661923132169163975144209858469968755; } //!< \returns The value of \f$\frac{\pi}{2}\f$ with the highest precision for \f$genType\f$ -template constexpr genType three_halves_pi() { return 4.71238898038468985769396507491925432629575409906265; } //!< \returns The value of \f$\frac{3\pi}{2}\f$ with the highest precision for \f$genType\f$ +template constexpr genType half_pi() { return 1.57079632679489661923132169163975144209858469968755; } //!< \returns The value of \math{\frac{\pi}{2}} with the highest precision for \emph{genType} +template constexpr genType three_halves_pi() { return 4.71238898038468985769396507491925432629575409906265; } //!< \returns The value of \math{\frac{3\pi}{2}} with the highest precision for \emph{genType} -template constexpr genType third_pi() { return 1.04719755119659774615421446109316762806572313312503; } //!< \returns The value of \f$\frac{\pi}{3}\f$ with the highest precision for \f$genType\f$ -template constexpr genType two_thirds_pi() { return 2.09439510239319549230842892218633525613144626625007; } //!< \returns The value of \f$\frac{2\pi}{3}\f$ with the highest precision for \f$genType\f$ -template constexpr genType four_thirds_pi() { return 4.18879020478639098461685784437267051226289253250014; } //!< \returns The value of \f$\frac{4\pi}{3}\f$ with the highest precision for \f$genType\f$ -template constexpr genType five_thirds_pi() { return 5.23598775598298873077107230546583814032861566562517; } //!< \returns The value of \f$\frac{5\pi}{3}\f$ with the highest precision for \f$genType\f$ +template constexpr genType third_pi() { return 1.04719755119659774615421446109316762806572313312503; } //!< \returns The value of \math{\frac{\pi}{3}} with the highest precision for \emph{genType} +template constexpr genType two_thirds_pi() { return 2.09439510239319549230842892218633525613144626625007; } //!< \returns The value of \math{\frac{2\pi}{3}} with the highest precision for \emph{genType} +template constexpr genType four_thirds_pi() { return 4.18879020478639098461685784437267051226289253250014; } //!< \returns The value of \math{\frac{4\pi}{3}} with the highest precision for \emph{genType} +template constexpr genType five_thirds_pi() { return 5.23598775598298873077107230546583814032861566562517; } //!< \returns The value of \math{\frac{5\pi}{3}} with the highest precision for \emph{genType} -template constexpr genType quarter_pi() { return 0.78539816339744830961566084581987572104929234984377; } //!< \returns The value of \f$\frac{\pi}{4}\f$ with the highest precision for \f$genType\f$ -template constexpr genType three_quarters_pi() { return 2.35619449019234492884698253745962716314787704953132; } //!< \returns The value of \f$\frac{3\pi}{4}\f$ with the highest precision for \f$genType\f$ -template constexpr genType five_quarters_pi() { return 3.92699081698724154807830422909937860524646174921888; } //!< \returns The value of \f$\frac{5\pi}{4}\f$ with the highest precision for \f$genType\f$ -template constexpr genType seven_quarters_pi() { return 5.49778714378213816730962592073913004734504644890643; } //!< \returns The value of \f$\frac{7\pi}{4}\f$ with the highest precision for \f$genType\f$ +template constexpr genType quarter_pi() { return 0.78539816339744830961566084581987572104929234984377; } //!< \returns The value of \math{\frac{\pi}{4}} with the highest precision for \emph{genType} +template constexpr genType three_quarters_pi() { return 2.35619449019234492884698253745962716314787704953132; } //!< \returns The value of \math{\frac{3\pi}{4}} with the highest precision for \emph{genType} +template constexpr genType five_quarters_pi() { return 3.92699081698724154807830422909937860524646174921888; } //!< \returns The value of \math{\frac{5\pi}{4}} with the highest precision for \emph{genType} +template constexpr genType seven_quarters_pi() { return 5.49778714378213816730962592073913004734504644890643; } //!< \returns The value of \math{\frac{7\pi}{4}} with the highest precision for \emph{genType} -template constexpr genType fifth_pi() { return 0.62831853071795864769252867665590057683943387987502; } //!< \returns The value of \f$\frac{\pi}{5}\f$ with the highest precision for \f$genType\f$ -template constexpr genType two_fifths_pi() { return 1.25663706143591729538505735331180115367886775975004; } //!< \returns The value of \f$\frac{2\pi}{5}\f$ with the highest precision for \f$genType\f$ -template constexpr genType three_fifths_pi() { return 1.88495559215387594307758602996770173051830163962506; } //!< \returns The value of \f$\frac{3\pi}{5}\f$ with the highest precision for \f$genType\f$ -template constexpr genType four_fifths_pi() { return 2.51327412287183459077011470662360230735773551950008; } //!< \returns The value of \f$\frac{4\pi}{5}\f$ with the highest precision for \f$genType\f$ -template constexpr genType six_fifths_pi() { return 3.76991118430775188615517205993540346103660327925012; } //!< \returns The value of \f$\frac{6\pi}{5}\f$ with the highest precision for \f$genType\f$ -template constexpr genType seven_fifths_pi() { return 4.39822971502571053384770073659130403787603715912514; } //!< \returns The value of \f$\frac{7\pi}{5}\f$ with the highest precision for \f$genType\f$ -template constexpr genType eight_fifths_pi() { return 5.02654824574366918154022941324720461471547103900016; } //!< \returns The value of \f$\frac{8\pi}{5}\f$ with the highest precision for \f$genType\f$ -template constexpr genType nine_fifths_pi() { return 5.65486677646162782923275808990310519155490491887519; } //!< \returns The value of \f$\frac{9\pi}{5}\f$ with the highest precision for \f$genType\f$ +template constexpr genType fifth_pi() { return 0.62831853071795864769252867665590057683943387987502; } //!< \returns The value of \math{\frac{\pi}{5}} with the highest precision for \emph{genType} +template constexpr genType two_fifths_pi() { return 1.25663706143591729538505735331180115367886775975004; } //!< \returns The value of \math{\frac{2\pi}{5}} with the highest precision for \emph{genType} +template constexpr genType three_fifths_pi() { return 1.88495559215387594307758602996770173051830163962506; } //!< \returns The value of \math{\frac{3\pi}{5}} with the highest precision for \emph{genType} +template constexpr genType four_fifths_pi() { return 2.51327412287183459077011470662360230735773551950008; } //!< \returns The value of \math{\frac{4\pi}{5}} with the highest precision for \emph{genType} +template constexpr genType six_fifths_pi() { return 3.76991118430775188615517205993540346103660327925012; } //!< \returns The value of \math{\frac{6\pi}{5}} with the highest precision for \emph{genType} +template constexpr genType seven_fifths_pi() { return 4.39822971502571053384770073659130403787603715912514; } //!< \returns The value of \math{\frac{7\pi}{5}} with the highest precision for \emph{genType} +template constexpr genType eight_fifths_pi() { return 5.02654824574366918154022941324720461471547103900016; } //!< \returns The value of \math{\frac{8\pi}{5}} with the highest precision for \emph{genType} +template constexpr genType nine_fifths_pi() { return 5.65486677646162782923275808990310519155490491887519; } //!< \returns The value of \math{\frac{9\pi}{5}} with the highest precision for \emph{genType} -template constexpr genType sixth_pi() { return 0.52359877559829887307710723054658381403286156656251; } //!< \returns The value of \f$\frac{\pi}{6}\f$ with the highest precision for \f$genType\f$ -template constexpr genType five_sixths_pi() { return 2.61799387799149436538553615273291907016430783281258; } //!< \returns The value of \f$\frac{5\pi}{6}\f$ with the highest precision for \f$genType\f$ -template constexpr genType seven_sixths_pi() { return 3.66519142918809211153975061382608669823003096593762; } //!< \returns The value of \f$\frac{7\pi}{6}\f$ with the highest precision for \f$genType\f$ -template constexpr genType eleven_sixths_pi() { return 5.75958653158128760384817953601242195436147723218769; } //!< \returns The value of \f$\frac{11\pi}{6}\f$ with the highest precision for \f$genType\f$ +template constexpr genType sixth_pi() { return 0.52359877559829887307710723054658381403286156656251; } //!< \returns The value of \math{\frac{\pi}{6}} with the highest precision for \emph{genType} +template constexpr genType five_sixths_pi() { return 2.61799387799149436538553615273291907016430783281258; } //!< \returns The value of \math{\frac{5\pi}{6}} with the highest precision for \emph{genType} +template constexpr genType seven_sixths_pi() { return 3.66519142918809211153975061382608669823003096593762; } //!< \returns The value of \math{\frac{7\pi}{6}} with the highest precision for \emph{genType} +template constexpr genType eleven_sixths_pi() { return 5.75958653158128760384817953601242195436147723218769; } //!< \returns The value of \math{\frac{11\pi}{6}} with the highest precision for \emph{genType} // Reciprocals of Pi -template constexpr genType one_over_pi() { return 0.31830988618379067153776752674502872406891929148091; } //!< \returns The value of \f$\frac{1}{\pi}\f$ with the highest precision for \f$genType\f$ -template constexpr genType two_over_pi() { return 0.63661977236758134307553505349005744813783858296182; } //!< \returns The value of \f$\frac{2}{\pi}\f$ with the highest precision for \f$genType\f$ +template constexpr genType one_over_pi() { return 0.31830988618379067153776752674502872406891929148091; } //!< \returns The value of \math{\frac{1}{\pi}} with the highest precision for \emph{genType} +template constexpr genType two_over_pi() { return 0.63661977236758134307553505349005744813783858296182; } //!< \returns The value of \math{\frac{2}{\pi}} with the highest precision for \emph{genType} // Exponentiations Pi -template constexpr genType pi_sq() { return 9.86960440108935861883449099987615113531369940724079; } //!< \returns The value of \f${\pi}^{2}\f$ with the highest precision for \f$genType\f$ -template constexpr genType pi_cb() { return 31.00627668029982017547631506710139520222528856588510; } //!< \returns The value of \f${\pi}^{2}\f$ with the highest precision for \f$genType\f$ -template constexpr genType sqrt_pi() { return 1.77245385090551602729816748334114518279754945612238; } ///< \returns The value of \f$\sqrt{\pi}\f$ with the highest precision for \f$genType\f$ -template constexpr genType one_over_sqrt_pi() { return 0.56418958354775628694807945156077258584405062932899; } ///< \returns The value of \f$\frac{1}{\sqrt{\pi}}\f$ with the highest precision for \f$genType\f$ -template constexpr genType sqrt_two_pi() { return 1.77245385090551602729816748334114518279754945612238; } ///< \returns The value of \f$\sqrt{2\pi}\f$ with the highest precision for \f$genType\f$ -template constexpr genType one_over_sqrt_two_pi() { return 0.39894228040143267793994605993438186847585863116493; } ///< \returns The value of \f$\frac{1}{\sqrt{2\pi}}\f$ with the highest precision for \f$genType\f$ -template constexpr genType cbrt_pi() { return 1.46459188756152326302014252726379039173859685562793; } ///< \returns The value of \f$\sqrt[3]{\pi}\f$ with the highest precision for \f$genType\f$ +template constexpr genType pi_sq() { return 9.86960440108935861883449099987615113531369940724079; } //!< \returns The value of \math{{\pi}^{2}} with the highest precision for \emph{genType} +template constexpr genType pi_cb() { return 31.00627668029982017547631506710139520222528856588510; } //!< \returns The value of \math{{\pi}^{2}} with the highest precision for \emph{genType} +template constexpr genType sqrt_pi() { return 1.77245385090551602729816748334114518279754945612238; } ///< \returns The value of \math{\sqrt{\pi}} with the highest precision for \emph{genType} +template constexpr genType one_over_sqrt_pi() { return 0.56418958354775628694807945156077258584405062932899; } ///< \returns The value of \math{\frac{1}{\sqrt{\pi}}} with the highest precision for \emph{genType} +template constexpr genType sqrt_two_pi() { return 1.77245385090551602729816748334114518279754945612238; } ///< \returns The value of \math{\sqrt{2\pi}} with the highest precision for \emph{genType} +template constexpr genType one_over_sqrt_two_pi() { return 0.39894228040143267793994605993438186847585863116493; } ///< \returns The value of \math{\frac{1}{\sqrt{2\pi}}} with the highest precision for \emph{genType} +template constexpr genType cbrt_pi() { return 1.46459188756152326302014252726379039173859685562793; } ///< \returns The value of \math{\sqrt[3]{\pi}} with the highest precision for \emph{genType} // e =================================================================================================================== // Multiples and Reciprocal -template constexpr genType e() { return 2.71828182845904523536028747135266249775724709369995; } ///< \returns The value of \f$e\f$ with the highest precision for \f$genType\f$ -template constexpr genType half_e() { return 1.35914091422952261768014373567633124887862354684997; } ///< \returns The value of \f$\frac{e}{2}\f$ with the highest precision for \f$genType\f$ -template constexpr genType two_e() { return 5.43656365691809047072057494270532499551449418739991; } ///< \returns The value of \f$2e\f$ with the highest precision for \f$genType\f$ -template constexpr genType one_over_e() { return 0.36787944117144232159552377016146086744581113103176; } ///< \returns The value of \f$\frac{1}{e}\f$ with the highest precision for \f$genType\f$ +template constexpr genType e() { return 2.71828182845904523536028747135266249775724709369995; } ///< \returns The value of \math{e} with the highest precision for \emph{genType} +template constexpr genType half_e() { return 1.35914091422952261768014373567633124887862354684997; } ///< \returns The value of \math{\frac{e}{2}} with the highest precision for \emph{genType} +template constexpr genType two_e() { return 5.43656365691809047072057494270532499551449418739991; } ///< \returns The value of \math{2e} with the highest precision for \emph{genType} +template constexpr genType one_over_e() { return 0.36787944117144232159552377016146086744581113103176; } ///< \returns The value of \math{\frac{1}{e}} with the highest precision for \emph{genType} // Exponentiations of e -template constexpr genType e_sq() { return 7.38905609893065022723042746057500781318031557055184; } ///< \returns The value of \f$e^2\f$ with the highest precision for \f$genType\f$ -template constexpr genType e_cb() { return 20.08553692318766774092852965458171789698790783855415; } ///< \returns The value of \f$e^3\f$ with the highest precision for \f$genType\f$ -template constexpr genType sqrt_e() { return 1.64872127070012814684865078781416357165377610071014; } ///< \returns The value of \f$\sqrt{e}\f$ with the highest precision for \f$genType\f$ -template constexpr genType one_over_sqrt_e() { return 0.60653065971263342360379953499118045344191813548718; } ///< \returns The value of \f$\frac{1}{\sqrt{e}}\f$ with the highest precision for \f$genType\f$ -template constexpr genType e_raised_two() { return 7.38905609893065022723042746057500781318031557055184; } ///< \returns The value of \f$e^e\f$ with the highest precision for \f$genType\f$ -template constexpr genType e_raised_e() { return 15.15426224147926418976043027262991190552854853685613; } ///< \returns The value of \f$e^e\f$ with the highest precision for \f$genType\f$ -template constexpr genType e_raised_neg_e() { return 0.065988035845312537076790187596846424938577048252796; } ///< \returns The value of \f$e^-e\f$ with the highest precision for \f$genType\f$ +template constexpr genType e_sq() { return 7.38905609893065022723042746057500781318031557055184; } ///< \returns The value of \math{e^2} with the highest precision for \emph{genType} +template constexpr genType e_cb() { return 20.08553692318766774092852965458171789698790783855415; } ///< \returns The value of \math{e^3} with the highest precision for \emph{genType} +template constexpr genType sqrt_e() { return 1.64872127070012814684865078781416357165377610071014; } ///< \returns The value of \math{\sqrt{e}} with the highest precision for \emph{genType} +template constexpr genType one_over_sqrt_e() { return 0.60653065971263342360379953499118045344191813548718; } ///< \returns The value of \math{\frac{1}{\sqrt{e}}} with the highest precision for \emph{genType} +template constexpr genType e_raised_two() { return 7.38905609893065022723042746057500781318031557055184; } ///< \returns The value of \math{e^e} with the highest precision for \emph{genType} +template constexpr genType e_raised_e() { return 15.15426224147926418976043027262991190552854853685613; } ///< \returns The value of \math{e^e} with the highest precision for \emph{genType} +template constexpr genType e_raised_neg_e() { return 0.065988035845312537076790187596846424938577048252796; } ///< \returns The value of \math{e^-e} with the highest precision for \emph{genType} // Exponentiations of e by Pi -template constexpr genType e_raised_pi() { return 23.14069263277926900572908636794854738026610624260021; } ///< \returns The value of \f${e}^{ \pi}\f$ with the highest precision for \f$genType\f$ -template constexpr genType e_raised_neg_pi() { return 0.04321391826377224977441773717172801127572810981063; } ///< \returns The value of \f${e}^{-\pi}\f$ with the highest precision for \f$genType\f$ -template constexpr genType e_raised_half_pi() { return 4.81047738096535165547303566670383312639017087466453; } ///< \returns The value of \f${e}^{\frac{ \pi}{2}}\f$ with the highest precision for \f$genType\f$ -template constexpr genType e_raised_neg_half_pi() { return 0.20787957635076190854695561983497877003387784163176; } ///< \returns The value of \f${e}^{\frac{-\pi}{2}}\f$ with the highest precision for \f$genType\f$ +template constexpr genType e_raised_pi() { return 23.14069263277926900572908636794854738026610624260021; } ///< \returns The value of \math{{e}^{ \pi}} with the highest precision for \emph{genType} +template constexpr genType e_raised_neg_pi() { return 0.04321391826377224977441773717172801127572810981063; } ///< \returns The value of \math{{e}^{-\pi}} with the highest precision for \emph{genType} +template constexpr genType e_raised_half_pi() { return 4.81047738096535165547303566670383312639017087466453; } ///< \returns The value of \math{{e}^{\frac{ \pi}{2}}} with the highest precision for \emph{genType} +template constexpr genType e_raised_neg_half_pi() { return 0.20787957635076190854695561983497877003387784163176; } ///< \returns The value of \math{{e}^{\frac{-\pi}{2}}} with the highest precision for \emph{genType} // Exponentiations of e by Gamma -template constexpr genType e_raised_gamma() { return 1.78107241799019798523650410310717954916964521430343; } ///< \returns The value of \f${e}^{ \gamma}\f$ with the highest precision for \f$genType\f$ -template constexpr genType e_raised_neg_gamma() { return 0.56145948356688516982414321479088078676571038692515; } ///< \returns The value of \f${e}^{-\gamma}\f$ with the highest precision for \f$genType\f$ +template constexpr genType e_raised_gamma() { return 1.78107241799019798523650410310717954916964521430343; } ///< \returns The value of \math{{e}^{ \gamma}} with the highest precision for \emph{genType} +template constexpr genType e_raised_neg_gamma() { return 0.56145948356688516982414321479088078676571038692515; } ///< \returns The value of \math{{e}^{-\gamma}} with the highest precision for \emph{genType} // Catalan's Constant ================================================================================================== -template constexpr genType G() { return 0.91596559417721901505460351493238411077414937428167; } ///< \returns The value of \f$G\f$ with the highest precision for \f$genType\f$ -template constexpr genType one_over_G() { return 1.09174406370390610145415947333389232498605012140824; } ///< \returns The value of \f$\frac{1}{G}\f$ with the highest precision for \f$genType\f$ -template constexpr genType G_over_pi() { return 0.29156090403081878013838445646839491886406615398583; } ///< \returns The value of \f$\frac{G}{\pi}\f$ with the highest precision for \f$genType\f$ -template constexpr genType pi_over_G() { return 3.42981513013245864263455323784799901211670795530093; } ///< \returns The value of \f$\frac{\pi}{G}\f$ with the highest precision for \f$genType\f$ +template constexpr genType G() { return 0.91596559417721901505460351493238411077414937428167; } ///< \returns The value of \math{G} with the highest precision for \emph{genType} +template constexpr genType one_over_G() { return 1.09174406370390610145415947333389232498605012140824; } ///< \returns The value of \math{\frac{1}{G}} with the highest precision for \emph{genType} +template constexpr genType G_over_pi() { return 0.29156090403081878013838445646839491886406615398583; } ///< \returns The value of \math{\frac{G}{\pi}} with the highest precision for \emph{genType} +template constexpr genType pi_over_G() { return 3.42981513013245864263455323784799901211670795530093; } ///< \returns The value of \math{\frac{\pi}{G}} with the highest precision for \emph{genType} // Gamma =============================================================================================================== -template constexpr genType y() { return 0.57721566490153286060651209008240243104215933593992; } ///< \returns The value of \f$\gamma\f$ with the highest precision for \f$genType\f$ -template constexpr genType one_over_y() { return 1.73245471460063347358302531586082968115577655226680; } ///< \returns The value of \f$\frac{1}{\gamma}\f$ with the highest precision for \f$genType\f$ +template constexpr genType y() { return 0.57721566490153286060651209008240243104215933593992; } ///< \returns The value of \math{\gamma} with the highest precision for \emph{genType} +template constexpr genType one_over_y() { return 1.73245471460063347358302531586082968115577655226680; } ///< \returns The value of \math{\frac{1}{\gamma}} with the highest precision for \emph{genType} // Logarithms ========================================================================================================== -template constexpr genType log_two() { return 0.69314718055994530941723212145817656807550013436025; } ///< \returns The value of \f$\log{2}\f$ with the highest precision for \f$genType\f$ -template constexpr genType log_three() { return 1.09861228866810969139524523692252570464749055782274; } ///< \returns The value of \f$\log{3}\f$ with the highest precision for \f$genType\f$ -template constexpr genType log_five() { return 1.60943791243410037460075933322618763952560135426851; } ///< \returns The value of \f$\log{5}\f$ with the highest precision for \f$genType\f$ -template constexpr genType log_seven() { return 1.94591014905531330510535274344317972963708472958186; } ///< \returns The value of \f$\log{7}\f$ with the highest precision for \f$genType\f$ -template constexpr genType log_ten() { return 2.30258509299404568401799145468436420760110148862877; } ///< \returns The value of \f$\log{10}\f$ with the highest precision for \f$genType\f$ -template constexpr genType one_over_log_ten() { return 0.43429448190325182765112891891660508229439700580366; } ///< \returns The value of \f$\frac{1}{\log{10}}\f$ with the highest precision for \f$genType\f$ -template constexpr genType log_two_over_log_three() { return 0.63092975357145743709952711434276085429958564013188; } ///< \returns The value of \f$\frac{\log{2}}{\log{3}}\f$ with the highest precision for \f$genType\f$ -template constexpr genType log_log_two() { return -0.36651292058166432701243915823266946945426344783711; } ///< \returns The value of \f$\log{\log{2}}\f$ with the highest precision for \f$genType\f$ -template constexpr genType log_pi() { return 1.14472988584940017414342735135305871164729481291531; } ///< \returns The value of \f$\log{\pi}\f$ with the highest precision for \f$genType\f$ -template constexpr genType log_sqrt_two() { return 0.91893853320467274178032973640561763986139747363778; } ///< \returns The value of \f$\log{\sqrt{2}}\f$ with the highest precision for \f$genType\f$ -template constexpr genType log_gamma() { return -0.54953931298164482233766176880290778833069898126306; } ///< \returns The value of \f$\log{\gamma}\f$ with the highest precision for \f$genType\f$ -template constexpr genType log_phi() { return 0.48121182505960344749775891342436842313518433438566; } ///< \returns The value of \f$\log{\phi}\f$ with the highest precision for \f$genType\f$ +template constexpr genType log_two() { return 0.69314718055994530941723212145817656807550013436025; } ///< \returns The value of \math{\log{2}} with the highest precision for \emph{genType} +template constexpr genType log_three() { return 1.09861228866810969139524523692252570464749055782274; } ///< \returns The value of \math{\log{3}} with the highest precision for \emph{genType} +template constexpr genType log_five() { return 1.60943791243410037460075933322618763952560135426851; } ///< \returns The value of \math{\log{5}} with the highest precision for \emph{genType} +template constexpr genType log_seven() { return 1.94591014905531330510535274344317972963708472958186; } ///< \returns The value of \math{\log{7}} with the highest precision for \emph{genType} +template constexpr genType log_ten() { return 2.30258509299404568401799145468436420760110148862877; } ///< \returns The value of \math{\log{10}} with the highest precision for \emph{genType} +template constexpr genType one_over_log_ten() { return 0.43429448190325182765112891891660508229439700580366; } ///< \returns The value of \math{\frac{1}{\log{10}}} with the highest precision for \emph{genType} +template constexpr genType log_two_over_log_three() { return 0.63092975357145743709952711434276085429958564013188; } ///< \returns The value of \math{\frac{\log{2}}{\log{3}}} with the highest precision for \emph{genType} +template constexpr genType log_log_two() { return -0.36651292058166432701243915823266946945426344783711; } ///< \returns The value of \math{\log{\log{2}}} with the highest precision for \emph{genType} +template constexpr genType log_pi() { return 1.14472988584940017414342735135305871164729481291531; } ///< \returns The value of \math{\log{\pi}} with the highest precision for \emph{genType} +template constexpr genType log_sqrt_two() { return 0.91893853320467274178032973640561763986139747363778; } ///< \returns The value of \math{\log{\sqrt{2}}} with the highest precision for \emph{genType} +template constexpr genType log_gamma() { return -0.54953931298164482233766176880290778833069898126306; } ///< \returns The value of \math{\log{\gamma}} with the highest precision for \emph{genType} +template constexpr genType log_phi() { return 0.48121182505960344749775891342436842313518433438566; } ///< \returns The value of \math{\log{\phi}} with the highest precision for \emph{genType} } diff --git a/include/fennec/math/ext/quaternion.h b/include/fennec/math/ext/quaternion.h index c03bdcf..dc61965 100644 --- a/include/fennec/math/ext/quaternion.h +++ b/include/fennec/math/ext/quaternion.h @@ -52,7 +52,7 @@ constexpr genType sqnorm(const qua& q) { /// /// \brief Norm Function /// \param q The Quaternion -/// \returns The Hamilton Tensor of \f$q\f$ +/// \returns The Hamilton Tensor of \emph{q} template constexpr genType norm(const qua& q) { return fennec::sqrt(sqnorm(q)); @@ -61,7 +61,7 @@ constexpr genType norm(const qua& q) { /// /// \brief Unit Function (Versor) /// \param q The Quaternion -/// \returns A Quaternion of \f$q\f$ with norm \f$1\f$ +/// \returns A Quaternion of \emph{q} with norm \math{1} template constexpr qua unit(const qua& q) { genType n = fennec::norm(q); @@ -71,7 +71,7 @@ constexpr qua unit(const qua& q) { /// /// \brief Reciprocal Function /// \param q The Quaternion -/// \returns The quaternion \f${q}^{-1}\f$ +/// \returns The quaternion \math{\textbf{q}^{-1}} template constexpr qua reciprocal(const qua& q) { return ~q / fennec::sqnorm(q); @@ -99,7 +99,7 @@ public: // Constructors ======================================================================================================== /// - /// \brief Default Constructor, creates a quaternion such that the real part is \f$1\f$ and all others are \f$0\f$ + /// \brief Default Constructor, creates a quaternion such that the real part is \math{1} and all others are \math{0} constexpr quaternion() { data = { 0, 0, 0, 1 }; } @@ -107,9 +107,9 @@ public: /// /// \brief Component Constructor /// \param w The scalar component - /// \param x The coefficient of the \f$i\f$ component - /// \param y The coefficient of the \f$j\f$ component - /// \param z The coefficient of the \f$k\f$ component + /// \param x The coefficient of the \emph{i} component + /// \param y The coefficient of the \emph{j} component + /// \param z The coefficient of the \emph{k} component constexpr quaternion(scalar_t w, scalar_t x, scalar_t y, scalar_t z) { data = { x, y, z, w }; } @@ -160,7 +160,7 @@ public: /// /// \brief Copy Assignment Operator /// \param q The quaternion to copy - /// \returns a reference to self + /// \returns a reference to \emph{this} constexpr quat_t& operator=(const quat_t& q) { data = q.data; return *this; @@ -169,7 +169,7 @@ public: /// /// \brief Move Assignment Operator /// \param q The quaternion to move - /// \returns a reference to self + /// \returns a reference to \emph{this} constexpr quat_t& operator=(quat_t&& q) noexcept { data = q.data; return *this; @@ -182,7 +182,7 @@ public: /// \brief Equality Operator /// \param lhs the left hand side of the expression /// \param rhs the right hand side of the expression - /// \returns \f$true\f$ when all components of \f$lhs\f$ and \f$rhs\f$ are equal, false otherwise + /// \returns \emph{true} when all components of \emph{lhs} and \emph{rhs} are equal, false otherwise constexpr friend bool operator==(const quat_t& lhs, const quat_t& rhs) { return lhs.data == rhs.data; } @@ -191,7 +191,7 @@ public: /// \brief Inequality Operator /// \param lhs the left hand side of the expression /// \param rhs the right hand side of the expression - /// \returns \f$true\f$ when any component of \f$lhs\f$ and \f$rhs\f$ are not equal, false otherwise + /// \returns \emph{true} when any component of \emph{lhs} and \emph{rhs} are not equal, false otherwise constexpr friend bool operator!=(const quat_t& lhs, const quat_t& rhs) { return lhs.data != rhs.data; } @@ -202,7 +202,7 @@ public: /// /// \brief Unary Negation Operator /// \param rhs The quaternion to negate - /// \returns A quaternion with each component of \f$rhs\f$ negated. + /// \returns A quaternion with each component of \emph{rhs} negated. constexpr friend quat_t operator-(const quat_t& rhs) { return quat_t(-rhs.w, -rhs.x, -rhs.y, -rhs.z); } @@ -210,7 +210,7 @@ public: /// /// \brief Unary Conjugation Operator /// \param rhs The quaternion to conjugate - /// \returns A quaternion with each vector component of \f$rhs\f$ negated. + /// \returns A quaternion with each vector component of \emph{rhs} negated. constexpr friend quat_t operator~(const quat_t& rhs) { return quat_t(rhs.w, -rhs.x, -rhs.y, -rhs.z); } @@ -222,7 +222,7 @@ public: /// \brief Quaternion-Scalar Multiplication Operator /// \param lhs The quaternion /// \param rhs The scalar - /// \returns A quaternion with each component of \f$lhs\f$ multiplied by \f$rhs\f$ + /// \returns A quaternion with each component of \emph{lhs} multiplied by \emph{rhs} constexpr friend quat_t operator*(const quat_t& lhs, scalar_t rhs) { return quat_t(lhs.w * rhs, lhs.x * rhs, lhs.y * rhs, lhs.z * rhs); } @@ -231,7 +231,7 @@ public: /// \brief Scalar-Quaternion Multiplication Operator /// \param lhs The scalar /// \param rhs The quaternion - /// \returns A quaternion with each component of \f$rhs\f$ multiplied by \f$lhs\f$ + /// \returns A quaternion with each component of \emph{rhs} multiplied by \emph{lhs} constexpr friend quat_t operator*(scalar_t lhs, const quat_t& rhs) { return quat_t(lhs * rhs.w, lhs * rhs.x, lhs * rhs.y, lhs * rhs.z); } @@ -240,7 +240,7 @@ public: /// \brief Quaternion-Scalar Division Operator /// \param lhs The quaternion /// \param rhs The scalar - /// \returns A quaternion with each component of \f$lhs\f$ divided by \f$rhs\f$ + /// \returns A quaternion with each component of \emph{lhs} divided by \emph{rhs} constexpr friend quat_t operator/(const quat_t& lhs, scalar_t rhs) { return quat_t(lhs.w / rhs, lhs.x / rhs, lhs.y / rhs, lhs.z / rhs); } @@ -249,7 +249,7 @@ public: /// \brief Scalar-Quaternion Division Operator /// \param lhs The scalar /// \param rhs The quaternion - /// \returns A quaternion with each component of \f$rhs\f$ divided by \f$lhs\f$ + /// \returns A quaternion with each component of \emph{rhs} divided by \emph{lhs} constexpr friend quat_t operator/(scalar_t lhs, const quat_t& rhs) { return quat_t(lhs / rhs.w, lhs / rhs.x, lhs / rhs.y, lhs / rhs.z); } @@ -261,7 +261,7 @@ public: /// \brief Quaternion-Scalar Multiplication Assignment Operator /// \param lhs The quaternion /// \param rhs The scalar - /// \returns \f$lhs\f$ with each component multiplied by \f$rhs\f$ + /// \returns \emph{lhs} with each component multiplied by \emph{rhs} constexpr friend quat_t& operator*=(quat_t& lhs, scalar_t rhs) { lhs.x *= rhs; lhs.y *= rhs; @@ -274,7 +274,7 @@ public: /// \brief Quaternion-Scalar Division Assignment Operator /// \param lhs The quaternion /// \param rhs The scalar - /// \returns \f$lhs\f$ with each component divided by \f$rhs\f$ + /// \returns \emph{lhs} with each component divided by \emph{rhs} constexpr friend quat_t& operator/=(const quat_t& lhs, scalar_t rhs) { lhs.x /= rhs; lhs.y /= rhs; @@ -290,7 +290,7 @@ public: /// \brief Quaternion-Vector Multiplication Operator /// \param q the quaternion /// \param v the vector - /// \returns the linear algebraic product of \f$q\f$ and \f$v\f$ + /// \returns the linear algebraic product of \emph{q} and \emph{v} constexpr friend vec3_t operator*(const quat_t& q, const vec3_t& v) { const vec3_t u = q.xyz; const vec3_t uv = fennec::cross(u, v); @@ -302,7 +302,7 @@ public: /// \brief Vector-Quaternion Multiplication Operator /// \param v the vector /// \param q the quaternion - /// \returns the linear algebraic product of \f$v\f$ and \f$q\f$ + /// \returns the linear algebraic product of \emph{v} and \emph{q} constexpr friend vec3_t operator*(const vec3_t& v, const quat_t& q) { return fennec::reciprocal(q) * v; } @@ -311,7 +311,7 @@ public: /// \brief Quaternion-Vector Multiplication Operator /// \param q the quaternion /// \param v the vector - /// \returns the linear algebraic product of \f$q\f$ and \f$v\f$ + /// \returns the linear algebraic product of \emph{q} and \emph{v} constexpr friend vec4_t operator*(const quat_t& q, const vec4_t& v) { return vec4_t(q * v.xyz, v.w); } @@ -320,7 +320,7 @@ public: /// \brief Vector-Quaternion Multiplication Operator /// \param v the vector /// \param q the quaternion - /// \returns the linear algebraic product of \f$v\f$ and \f$q\f$ + /// \returns the linear algebraic product of \emph{v} and \emph{q} constexpr friend vec4_t operator*(const vec4_t& v, const quat_t& q) { return fennec::reciprocal(q) * v; } @@ -332,7 +332,7 @@ public: /// \brief Quaternion-Quaternion Addition Operator /// \param lhs the left hand side /// \param rhs the right hand side - /// \returns the component-wise sum of \f$lhs\f$ and \f$rhs\f$ + /// \returns the component-wise sum of \emph{lhs} and \emph{rhs} constexpr friend quat_t operator+(const quat_t& lhs, const quat_t& rhs) { return quat_t( lhs.w + rhs.w, @@ -346,7 +346,7 @@ public: /// \brief Quaternion-Quaternion Subtraction Operator /// \param lhs the left hand side /// \param rhs the right hand side - /// \returns the component-wise difference of \f$lhs\f$ and \f$rhs\f$ + /// \returns the component-wise difference of \emph{lhs} and \emph{rhs} constexpr friend quat_t operator-(const quat_t& lhs, const quat_t& rhs) { return quat_t( lhs.w - rhs.w, @@ -360,7 +360,7 @@ public: /// \brief Quaternion-Quaternion Multiplication Operator /// \param lhs the left hand side /// \param rhs the right hand side - /// \returns the linear algebraic product of \f$lhs\f$ and \f$rhs\f$ + /// \returns the linear algebraic product of \emph{lhs} and \emph{rhs} constexpr friend quat_t operator*(const quat_t& lhs, const quat_t& rhs) { return quat_t( lhs.w*rhs.w - lhs.x*rhs.x - lhs.y*rhs.y - lhs.z * rhs.z, @@ -377,7 +377,7 @@ public: /// \brief Quaternion-Quaternion Addition Assignment Operator /// \param lhs the left hand side /// \param rhs the right hand side - /// \returns the component-wise sum of \f$lhs\f$ and \f$rhs\f$ stored in \f$lhs\f$ + /// \returns the component-wise sum of \emph{lhs} and \emph{rhs} stored in \emph{lhs} constexpr friend quat_t& operator+=(quat_t& lhs, const quat_t& rhs) { lhs.w += rhs.w; lhs.x += rhs.x; @@ -390,7 +390,7 @@ public: /// \brief Quaternion-Quaternion Subtraction Assignment Operator /// \param lhs the left hand side /// \param rhs the right hand side - /// \returns the component-wise difference of \f$lhs\f$ and \f$rhs\f$ stored in \f$lhs\f$ + /// \returns the component-wise difference of \emph{lhs} and \emph{rhs} stored in \emph{lhs} constexpr friend quat_t& operator-=(quat_t& lhs, const quat_t& rhs) { lhs.w -= rhs.w; lhs.x -= rhs.x; @@ -403,7 +403,7 @@ public: /// \brief Quaternion-Quaternion Multiplication Assignment Operator /// \param lhs the left hand side /// \param rhs the right hand side - /// \returns the linear algebraic product of \f$lhs\f$ and \f$rhs\f$ stored in \f$lhs\f$ + /// \returns the linear algebraic product of \emph{lhs} and \emph{rhs} stored in \emph{lhs} constexpr friend quat_t& operator*=(quat_t& lhs, const quat_t& rhs) { return lhs = lhs * rhs; } diff --git a/include/fennec/math/geometric.h b/include/fennec/math/geometric.h index 9d1c0fc..97029c2 100644 --- a/include/fennec/math/geometric.h +++ b/include/fennec/math/geometric.h @@ -118,14 +118,14 @@ namespace fennec // dot ----------------------------------------------------------------------------------------------------------------- /// -/// \brief Returns the dot product of \f$x\f$ and \f$y\f$, i.e., \f$x_0 \cdot y_0 + x_1 \cdot y_1 + \ldots\f$ +/// \brief Returns the dot product of \math{x} and \math{y}, i.e., \math{x_0 \cdot y_0 + x_1 \cdot y_1 + \ldots} /// -/// \returns the dot product of \f$x\f$ and \f$y\f$, i.e., \f$x_0 \cdot y_0 + x_0 \cdot y_0 + \ldots\f$

+/// \returns the dot product of \math{x} and \math{y}, i.e., \math{x_0 \cdot y_0 + x_0 \cdot y_0 + \ldots}

/// \details we can represent this in linear algebra as the following,

-/// let \f$X=\left[\begin{array}\\ x_0 \\ x_1 \\ \vdots \\ x_N \end{array}\right]\f$
-/// let \f$Y=\left[\begin{array}\\ y_0 \\ y_1 \\ \vdots \\ y_N \end{array}\right]\f$

+/// let \math{X=\left[\begin{array}\\ x_0 \\ x_1 \\ \vdots \\ x_N \end{array}\right]}
+/// let \math{Y=\left[\begin{array}\\ y_0 \\ y_1 \\ \vdots \\ y_N \end{array}\right]}

/// -/// then \f$\text{dot}(X, Y)=X \cdot Y^T\f$

+/// then \math{\text{dot}(X, Y)=X \cdot Y^T}

/// /// \param x first vector /// \param y second vector @@ -138,13 +138,13 @@ constexpr genType dot(const vector& x, const vector
+/// \returns the squared length of vector \math{x}, i.e., \math{x_0^2 + x_1^2 + \ldots}

/// \details we can represent this in linear algebra as the following,

-/// let \f$X=\left[\begin{array}\\ x_0 \\ x_1 \\ \vdots \\ x_N \end{array}\right]\f$

+/// let \math{X=\left[\begin{array}\\ x_0 \\ x_1 \\ \vdots \\ x_N \end{array}\right]}

/// -/// then \f$\text{length2}(X)=X \cdot X^T\f$

+/// then \math{\text{length2}(X)=X \cdot X^T}

/// /// \param x the vector template @@ -156,13 +156,13 @@ constexpr genType length2(const vector& x) { // length -------------------------------------------------------------------------------------------------------------- /// -/// \brief Returns the length of vector \f$x\f$, i.e., \f$\sqrt{x_0^2 + x_1^2 + \ldots}\f$ +/// \brief Returns the length of vector \math{x}, i.e., \math{\sqrt{x_0^2 + x_1^2 + \ldots}} /// -/// \returns the length of vector \f$x\f$, i.e., \f$\sqrt{x_0^2 + x_1^2 + \ldots}\f$

+/// \returns the length of vector \math{x}, i.e., \math{\sqrt{x_0^2 + x_1^2 + \ldots}}

/// \details we can represent this in linear algebra as the following,

-/// let \f$X=\left[\begin{array}\\ x_0 \\ x_1 \\ \vdots \\ x_N \end{array}\right]\f$

+/// let \math{X=\left[\begin{array}\\ x_0 \\ x_1 \\ \vdots \\ x_N \end{array}\right]}

/// -/// then, \f$\text{length}(X)=\left|\left|X\right|\right|\f$

+/// then, \math{\text{length}(X)=\left|\left|X\right|\right|}

/// /// \param x the vector template @@ -174,14 +174,14 @@ constexpr genType length(const vector& x) { // distance ------------------------------------------------------------------------------------------------------------ /// -/// \brief Returns the length of vector \f$x\f$, i.e., \f$\sqrt{x_0^2 + x_1^2 + \ldots}\f$ +/// \brief Returns the length of vector \math{x}, i.e., \math{\sqrt{x_0^2 + x_1^2 + \ldots}} /// -/// \returns the distance between \f$p_0\f$ and \f$p_1\f$, i.e., \f$\left|{p_1-p_0}\right|\f$ +/// \returns the distance between \math{p_0} and \math{p_1}, i.e., \math{\left|{p_1-p_0}\right|} /// \details we can represent this in linear algebra as the following,

-/// let \f$X=\left[\begin{array}\\ x_0 \\ x_1 \\ \vdots \\ x_N \end{array}\right]\f$
-/// let \f$Y=\left[\begin{array}\\ y_0 \\ y_1 \\ \vdots \\ y_N \end{array}\right]\f$

+/// let \math{X=\left[\begin{array}\\ x_0 \\ x_1 \\ \vdots \\ x_N \end{array}\right]}
+/// let \math{Y=\left[\begin{array}\\ y_0 \\ y_1 \\ \vdots \\ y_N \end{array}\right]}

/// -/// then \f$\text{distance}(X, Y)=\left|\left|Y-X\right|\right|\f$

+/// then \math{\text{distance}(X, Y)=\left|\left|Y-X\right|\right|}

/// /// \param p0 first vector /// \param p1 second vector @@ -194,16 +194,16 @@ constexpr genType distance(const vector& p0, const vector
+/// \returns the cross product of \math{x} and \math{y}, i.e., +/// \math{\left({x_1 \cdot y_2 - y_1 \cdot x_2, x_2 \cdot y_0 - y_2 \cdot x_0, x_0 \cdot y_1 - y_0 \cdot x_1}\right)}

/// \details we can represent this in linear algebra as the following,

-/// let \f$X=\left[\begin{array}\\ x_0 \\ x_1 \\ \vdots \\ x_N \end{array}\right]\f$
-/// let \f$Y=\left[\begin{array}\\ y_0 \\ y_1 \\ \vdots \\ y_N \end{array}\right]\f$

+/// let \math{X=\left[\begin{array}\\ x_0 \\ x_1 \\ \vdots \\ x_N \end{array}\right]}
+/// let \math{Y=\left[\begin{array}\\ y_0 \\ y_1 \\ \vdots \\ y_N \end{array}\right]}

/// -/// then \f$\text{cross}(X, Y)=X \times Y\f$

+/// then \math{\text{cross}(X, Y)=X \times Y}

/// /// \param x first vector /// \param y second vector @@ -216,13 +216,13 @@ constexpr vector cross(const vector& x, const vect // normalize ----------------------------------------------------------------------------------------------------------- /// -/// \brief Returns a vector in the same direction as \f$x\f$, but with a length of \f$1\f$, i.e. +/// \brief Returns a vector in the same direction as \math{x}, but with a length of \math{1}, i.e. /// -/// \returns a vector in the same direction as \f$x\f$, but with a length of \f$1\f$, i.e.\f$\frac{x}{||x||}\f$

+/// \returns a vector in the same direction as \math{x}, but with a length of \math{1}, i.e.\math{\frac{x}{||x||}}

/// \details we can represent this in linear algebra as the following,

-/// let \f$X=\left[\begin{array}\\ x_0 \\ x_1 \\ \vdots \\ x_N \end{array}\right]\f$

+/// let \math{X=\left[\begin{array}\\ x_0 \\ x_1 \\ \vdots \\ x_N \end{array}\right]}

/// -/// then, \f$\text{length}(X)=\frac{X}{\left|\left|X\right|\right|}\f$

+/// then, \math{\text{length}(X)=\frac{X}{\left|\left|X\right|\right|}}

/// /// \param x template @@ -234,9 +234,9 @@ constexpr vector normalize(const vector& x) { // faceforward --------------------------------------------------------------------------------------------------------- /// -/// \brief If \f$\text{dot}(Nref, I)<0\f$ return \f$N\f$, otherwise return \f$-N\f$. +/// \brief If \math{\text{dot}(Nref, I)<0} return \math{N}, otherwise return \math{-N}. /// -/// \returns \f$N\f$ if \f$\text{dot}(Nref,I)<0\f$, otherwise, returns \f$-N\f$.

+/// \returns \math{N} if \math{\text{dot}(Nref,I)<0}, otherwise, returns \math{-N}.

/// /// \param N the vector /// \param I the incident @@ -250,11 +250,11 @@ constexpr vector faceforward(const vector& N, cons // reflect ------------------------------------------------------------------------------------------------------------- /// -/// \brief For the incident vector \f$I\f$ and surface orientation \f$N\f$, returns the reflection direction. +/// \brief For the incident vector \math{I} and surface orientation \math{N}, returns the reflection direction. /// -/// \returns The reflection direction, given the incident vector \f$I\f$ and surface orientation \f$N\f$

+/// \returns The reflection direction, given the incident vector \math{I} and surface orientation \math{N}

/// \details We can express this as,

-/// \f$\text{reflect}(I, N) = I - 2 N \cdot \text{dot}(N, I)\f$

+/// \math{\text{reflect}(I, N) = I - 2 N \cdot \text{dot}(N, I)}

/// /// \param I the incident /// \param N the surface orientation @@ -266,13 +266,13 @@ constexpr vector reflect(const vector& I, const ve // refract ------------------------------------------------------------------------------------------------------------- /// -/// \brief For the incident vector \f$I\f$ and surface normal \f$N\f$, and the ratio of indices of refraction \f$eta\f$, +/// \brief For the incident vector \math{I} and surface normal \math{N}, and the ratio of indices of refraction \math{eta}, /// return the refraction vector. /// -/// \returns The refraction vector, given the incident vector \f$I\f$, surface normal \f$N\f$, and ratio \f$eta\f$.

+/// \returns The refraction vector, given the incident vector \math{I}, surface normal \math{N}, and ratio \math{eta}.

/// \details The result is computed by the refraction equation,

-/// let \f$k=1.0-eta^2 \cdot (1.0 - \text{dot}(N, I)^2)\f$
-/// then, \f$\text{refract}(I, N, eta)=\begin{cases} 0.0 & k<0.0, \\ eta \cdot I - N \cdot (eta \cdot \text{dot}(N, I) + \sqrt{k}) \end{cases}\f$

+/// let \math{k=1.0-eta^2 \cdot (1.0 - \text{dot}(N, I)^2)}
+/// then, \math{\text{refract}(I, N, eta)=\begin{cases} 0.0 & k<0.0, \\ eta \cdot I - N \cdot (eta \cdot \text{dot}(N, I) + \sqrt{k}) \end{cases}}

/// /// \param I the incident /// \param N the surface normal diff --git a/include/fennec/math/matrix.h b/include/fennec/math/matrix.h index c0b27b2..fd5dd4e 100644 --- a/include/fennec/math/matrix.h +++ b/include/fennec/math/matrix.h @@ -56,10 +56,10 @@ namespace fennec /// -/// \brief returns a **copy** of the column \f$i\f$ of matrix \f$m\f$ +/// \brief returns a **copy** of the column \emph{i} of matrix \emph{m} /// \param m the matrix /// \param i the index of the row -/// \returns a **copy** of the column at index \f$i\f$ +/// \returns a **copy** of the column at index \emph{i} template constexpr vec column(const matrix& m, size_t i) noexcept { return m[i]; @@ -67,10 +67,10 @@ constexpr vec column(const matrix& m, size_ /// -/// \brief returns a **copy** of the row \f$i\f$ of matrix \f$m\f$ +/// \brief returns a **copy** of the row \emph{i} of matrix \emph{m} /// \param m the matrix /// \param i the index of the row -/// \returns a **copy** of the row at index \f$i\f$ +/// \returns a **copy** of the row at index \emph{i} template constexpr vec row(const matrix& m, size_t i) noexcept { return vec(m[cols][i]...); @@ -118,7 +118,7 @@ using dmat4x4 = tmat4x4; //!< Specification for size glsl double matri /// -/// \brief Multiply matrix \f$x\f$ by matrix \f$y\f$ component-wise. +/// \brief Multiply matrix \emph{x} by matrix \emph{y} component-wise. /// \details Multiply matrix x by matrix y component-wise, i.e., result[i][j] is the scalar product of x[i][j] and y[i][j].

/// Note: to get linear algebraic matrix multiplication, use /// the multiply operator (*) @@ -131,14 +131,14 @@ constexpr matrix matrixCompMult(const matrix outerProduct(const vector constexpr mat transpose(const matrix& m) noexcept { @@ -160,7 +160,7 @@ constexpr mat transpose(const matrix constexpr scalar determinant(const matrix&) noexcept { @@ -169,8 +169,8 @@ constexpr scalar determinant(const matrix&) noexcept { } /// -/// \brief Returns the determinant of \f$m\f$. -/// \returns \f$m^{-1}\f$ +/// \brief Returns the determinant of \emph{m}. +/// \returns \math{\textbf{m}^{-1}} template constexpr matrix inverse(const matrix&) noexcept { static_assert(false, "implementation undefined"); @@ -295,7 +295,7 @@ struct matrix /// \brief scalar constructor, initializes a diagonal matrix with a scale of \p s /// /// \details - /// This function creates a diagonal matrix such that ```vec3(2.0f)``` would result in a matrix + /// This function creates a diagonal matrix such that `(.*?)` would result in a matrix /// /// ///
0 1 2 @@ -359,17 +359,17 @@ struct matrix /// /// \details /// \param i the index - /// \returns the column at index \f$i\f$ + /// \returns the column at index \emph{i} constexpr column_t& operator[](size_t i) { return data[i]; } /// - /// \brief returns the column at index \f$i\f$ + /// \brief returns the column at index \emph{i} /// /// \details /// \param i the index - /// \returns the column at index \f$i\f$ + /// \returns the column at index \emph{i} constexpr const column_t& operator[](size_t i) const { return data[i]; } @@ -378,7 +378,7 @@ struct matrix /// \details /// \param i the column /// \param j the row - /// \returns the element in column \f$i\f$, row \f$j\f$ + /// \returns the element in column \emph{i}, row \emph{j} constexpr scalar_t& operator[](size_t i, size_t j) { return data[i][j]; } @@ -389,7 +389,7 @@ struct matrix /// \details /// \param i the column /// \param j the row - /// \returns the element in column \f$i\f$, row \f$j\f$ + /// \returns the element in column \emph{i}, row \emph{j} constexpr scalar_t operator[](size_t i, size_t j) const { return data[i][j]; } @@ -610,7 +610,7 @@ struct matrix /// \brief performs a linear algebraic multiply /// \param lhs the matrix /// \param rhs the vector - /// \returns a vector containing the dot products of \f$rhs\f$ with each row of \f$lhs\f$ + /// \returns a vector containing the dot products of \emph{rhs} with each row of \emph{lhs} constexpr friend column_t operator*(const matrix_t& lhs, const row_t& rhs) { return _mul(lhs, rhs); } @@ -619,7 +619,7 @@ struct matrix /// \brief performs a linear algebraic multiply /// \param lhs the vector /// \param rhs the matrix - /// \returns a vector containing the dot products of \f$lhs\f$ with each column of \f$rhs\f$ + /// \returns a vector containing the dot products of \emph{lhs} with each column of \emph{rhs} constexpr friend row_t operator*(const column_t& lhs, const matrix_t& rhs) { return row_t(fennec::dot(fennec::column(rhs, ColIndicesV), lhs) ...); } @@ -637,7 +637,7 @@ struct matrix /// \brief matrix comparison operator /// \param lhs the first matrix /// \param rhs the second matrix - /// \returns a boolean value that contains \f$true\f$ when all components of \f$lhs\f$ and \f$rhs\f$ are equal and \f$false\f$ otherwise + /// \returns a boolean value that contains \emph{true} when all components of \emph{lhs} and \emph{rhs} are equal and \emph{false} otherwise constexpr friend bool operator==(const matrix_t& lhs, const matrix_t& rhs) { return lhs.data == rhs.data; } @@ -646,7 +646,7 @@ struct matrix /// \brief matrix comparison operator /// \param lhs the first matrix /// \param rhs the second matrix - /// \returns a boolean value that contains \f$true\f$ when all components of \f$lhs\f$ and \f$rhs\f$ are not equal and \f$false\f$ otherwise + /// \returns a boolean value that contains \emph{true} when all components of \emph{lhs} and \emph{rhs} are not equal and \emph{false} otherwise constexpr friend bool operator!=(const matrix_t& lhs, const matrix_t& rhs) { return lhs.data != rhs.data; } @@ -666,7 +666,7 @@ struct matrix /// /// \brief performs a linear algebraic matrix multiplication assignment /// \param rhs the columns to multiply with - /// \returns a reference to self + /// \returns a reference to \emph{this} template requires(columns == ORowsV) constexpr matrix& operator*=(const matrix& rhs) { return *this = *this * rhs; @@ -682,7 +682,7 @@ public: /// /// \param mat the matrix to transpose - /// \returns \f$m^T\f$ + /// \returns \math{\textbf{m}^T} static constexpr matrix_t transpose(const transpose_t& mat) { return matrix_t(fennec::row(mat, ColIndicesV)...); } diff --git a/include/fennec/math/relational.h b/include/fennec/math/relational.h index fd9a72f..79bf6cb 100644 --- a/include/fennec/math/relational.h +++ b/include/fennec/math/relational.h @@ -103,7 +103,7 @@ /// \ref fennec_vector_not "bool not(bvec x)"
///
/// \details -/// \returns the component-wise logical complement of \f$x\f$.
+/// \returns the component-wise logical complement of \math{x}.
/// \param x the boolean vector to inverse
/// ///
@@ -189,9 +189,9 @@ constexpr vector notEqual(const vector& x, const /// -/// \brief Returns \f$true\f$ if any component of \f$x\f$ is \f$true\f$ +/// \brief Returns \math{true} if any component of \math{x} is \math{true} /// -/// \returns \f$true\f$ if any component of \f$x\f$ is \f$true\f$ +/// \returns \math{true} if any component of \math{x} is \math{true} /// \param x the boolean vector to test template constexpr genBType any(const vector& x) { @@ -199,9 +199,9 @@ constexpr genBType any(const vector& x) { } /// -/// \brief Returns \f$true\f$ if all components of \f$x\f$ are \f$true\f$ +/// \brief Returns \math{true} if all components of \math{x} are \math{true} /// -/// \returns \f$true\f$ if all components of \f$x\f$ are \f$true\f$ +/// \returns \math{true} if all components of \math{x} are \math{true} /// \param x the boolean vector to test template constexpr genBType all(const vector& x) { @@ -210,10 +210,10 @@ constexpr genBType all(const vector& x) { /// /// \anchor fennec_vector_not -/// \brief Returns the component-wise logical complement of \f$x\f$. +/// \brief Returns the component-wise logical complement of \math{x}. /// /// \details -/// \returns the component-wise logical complement of \f$x\f$. +/// \returns the component-wise logical complement of \math{x}. /// \param x the boolean vector to inverse template constexpr vector operator not(const vector& x) { diff --git a/include/fennec/math/scalar.h b/include/fennec/math/scalar.h index e14bb44..de1709f 100644 --- a/include/fennec/math/scalar.h +++ b/include/fennec/math/scalar.h @@ -41,7 +41,7 @@ /// /// \code #include \endcode /// -/// The fennecLibrary considers any type that passes ```is_arithmetic``` to be a \ref scalar "Scalar." Bools are +/// The fennecLibrary considers any type that passes `(.*?)` to be a \ref scalar "Scalar." Bools are /// supported as a logical type. /// /// The GLSL Specification, and fennecrespectively, defines the following scalar types: diff --git a/include/fennec/math/trigonometric.h b/include/fennec/math/trigonometric.h index ee7d934..5a4e5ce 100644 --- a/include/fennec/math/trigonometric.h +++ b/include/fennec/math/trigonometric.h @@ -157,13 +157,13 @@ namespace fennec /// @{ /// -/// \brief Converts \f$degrees\f$ to \f$radians\f$, i.e., \f$degrees\cdot\frac{180}{\pi}\f$ +/// \brief Converts \emph{degrees} to \emph{radians}, i.e., \math{degrees\cdot\frac{180}{\pi}} /// -/// \returns the angle \f$\theta\f$ in \f$radians\f$

-/// \details Converts \f$degrees\f$ to \f$radians\f$, i.e., \f$degrees\cdot\frac{180}{\pi}\f$

+/// \returns the angle \math{\theta} in \math{radians}

+/// \details Converts \emph{degrees} to \emph{radians}, i.e., \math{degrees\cdot\frac{180}{\pi}}

/// /// \tparam genType floating point type -/// \param degrees the angle \f$\theta\f$ in \f$degrees\f$ +/// \param degrees the angle \math{\theta} in \math{degrees} template constexpr genType radians(genType degrees) { return genType(degrees * 0.01745329251994329576923690768489); @@ -171,13 +171,13 @@ constexpr genType radians(genType degrees) { /// -/// \brief Converts \f$radians\f$ to \f$degrees\f$, i.e., \f$radians\cdot\frac{\pi}{180}\f$ +/// \brief Converts \emph{radians} to \emph{degrees}, i.e., \math{radians\cdot\frac{\pi}{180}} /// -/// \returns the angle \f$\theta\f$ in \f$degrees\f$

-/// \details Converts \f$radians\f$ to \f$degrees\f$, i.e., \f$radians\cdot\frac{\pi}{180}\f$

+/// \returns the angle \math{\theta} in \emph{degrees}

+/// \details Converts \emph{radians} to \emph{degrees}, i.e., \math{radians\cdot\frac{\pi}{180}}

/// /// \tparam genType floating point type -/// \param radians the angle \f$\theta\f$ in \f$radians\f$ +/// \param radians the angle \math{\theta} in \emph{radians} template constexpr genType degrees(genType radians) { return genType(radians * 57.29577951308232087679815481410517); @@ -195,11 +195,11 @@ constexpr genType degrees(genType radians) { /// /// \brief The standard trigonometric sine /// -/// \returns the sine of \f$\theta\f$ in the range \f$\left[-1,\,1\right]\f$

+/// \returns the sine of \math{\theta} in the range \math{\left[-1,\,1\right]}

/// \details The standard trigonometric sine

/// /// \tparam genType floating point type -/// \param x the angle \f$\theta\f$ in \f$radians\f$ +/// \param x the angle \math{\theta} in \math{radians} template constexpr genType sin(genType x) { return ::sin(x); @@ -209,11 +209,11 @@ constexpr genType sin(genType x) { /// /// \brief The Standard Trigonometric Cosine /// -/// \returns the cosine of \f$\theta\f$ in the range \f$\left[-1,\,1\right]\f$

+/// \returns the cosine of \math{\theta} in the range \math{\left[-1,\,1\right]}

/// \details The Standard Trigonometric Cosine

/// /// \tparam genType floating point type -/// \param x the angle \f$\theta\f$ in \f$radians\f$ +/// \param x the angle \math{\theta} in \emph{radians} template constexpr genType cos(genType x) { return ::cos(x); @@ -223,11 +223,11 @@ constexpr genType cos(genType x) { /// /// \brief The Standard Trigonometric Tangent /// -/// \returns The Tangent of \f$\theta\f$ in the Range \f$\left[-\inf,\,\inf\right]\f$

+/// \returns The Tangent of \math{\theta} in the Range \math{\left[-\inf,\,\inf\right]}

/// \details The Standard Trigonometric Tangent

/// /// \tparam genType floating point type -/// \param x The Angle \f$\theta\f$ in \f$radians\f$ +/// \param x The Angle \math{\theta} in \math{radians} template constexpr genType tan(genType x) { return ::tan(x); @@ -241,14 +241,14 @@ constexpr genType tan(genType x) { /// @{ /// -/// \brief Arc Sine. Returns an angle \f$\theta\f$ whose sine is /a x. +/// \brief Arc Sine. Returns an angle \math{\theta} whose sine is /a x. /// -/// \returns an angle \f$\theta\f$ whose sine is /a x.

+/// \returns an angle \math{\theta} whose sine is /a x.

/// \details Arc Sine. The range of values returned by this functions is -/// \f$\left[-\pi/2,\pi/2\right]\f$. Results are undefined if \f$\left|x\right|\,>\,1\f$.

+/// \math{\left[-\pi/2,\pi/2\right]}. Results are undefined if \math{\left|x\right|\,>\,1}.

/// /// \tparam genType floating point type -/// \param x The Sine Value produced by \f$\theta\f$ +/// \param x The Sine Value produced by \math{\theta} template constexpr genType asin(genType x) { return ::asin(x); @@ -256,14 +256,14 @@ constexpr genType asin(genType x) { /// -/// \brief Arc Cosine. Returns an angle \f$\theta\f$ whose cosine is /a x. +/// \brief Arc Cosine. Returns an angle \math{\theta} whose cosine is /a x. /// -/// \returns an angle \f$\theta\f$ whose cosine is /a x. +/// \returns an angle \math{\theta} whose cosine is /a x. /// \details Arc Cosine. The range of values returned by this functions is -/// \f$\left[0,\pi\right]\f$. Results are undefined if \f$\left|x\right|\,>\,1\f$. +/// \math{\left[0,\pi\right]}. Results are undefined if \math{\left|x\right|\,>\,1}. /// /// \tparam genType floating point type -/// \param x The Cosine Value produced by \f$\theta\f$ +/// \param x The Cosine Value produced by \math{\theta} template constexpr genType acos(genType x) { return ::acos(x); @@ -271,14 +271,14 @@ constexpr genType acos(genType x) { /// -/// \brief Arc Tangent. Returns an angle \f$\theta\f$ whose tangent is /a y_over_x. +/// \brief Arc Tangent. Returns an angle \math{\theta} whose tangent is /a y_over_x. /// -/// \returns an angle \f$\theta\f$ whose tangent is /a y_over_x. +/// \returns an angle \math{\theta} whose tangent is /a y_over_x. /// \details Arc Tangent. The range of values returned by this functions is -/// \f$\left[\frac{-\pi}{2},\frac{\pi}{2}\right]\f$. Results are undefined if \f$\left|x\right|\,>\,1\f$. +/// \math{\left[\frac{-\pi}{2},\frac{\pi}{2}\right]}. Results are undefined if \math{\left|x\right|\,>\,1}. /// /// \tparam genType floating point type -/// \param y_over_x The Cosine Value produced by \f$\theta\f$ +/// \param y_over_x The Cosine Value produced by \math{\theta} template constexpr genType atan(genType y_over_x) { return ::atan(y_over_x); @@ -286,15 +286,15 @@ constexpr genType atan(genType y_over_x) { /// -/// \brief Arc Tangent. Returns an angle whose tangent is \f$\frac{y}{x}\f$. +/// \brief Arc Tangent. Returns an angle whose tangent is \math{\frac{y}{x}}. /// -/// \returns an angle whose tangent is \f$\frac{y}{x}\f$.

+/// \returns an angle whose tangent is \math{\frac{y}{x}}.

/// \details Arc Tangent. The signs of \a x and \a y are used to determine what quadrant the angle is in. -/// The range of values returned by this functions is \f$\left[-\pi,\pi\right]\f$

+/// The range of values returned by this functions is \math{\left[-\pi,\pi\right]}

/// /// \tparam genType floating point type -/// \param y The Sine Value produced by \f$\theta\f$ -/// \param x The Cosine Value produced by \f$\theta\f$ +/// \param y The Sine Value produced by \math{\theta} +/// \param x The Cosine Value produced by \math{\theta} template constexpr genType atan(genType y, genType x) { return ::atan2(y, x); @@ -310,12 +310,12 @@ constexpr genType atan(genType y, genType x) { /// @{ /// -/// \brief Returns the Hyperbolic Sine Function, \f$\frac{{e}^{x}-{e}^{-x}}{2}\f$ +/// \brief Returns the Hyperbolic Sine Function, \math{\frac{{e}^{x}-{e}^{-x}}{2}} /// -/// \returns The Hyperbolic Sine of \f$x\f$, \f$\frac{{e}^{x}-{e}^{-x}}{2}\f$

+/// \returns The Hyperbolic Sine of \math{x}, \math{\frac{{e}^{x}-{e}^{-x}}{2}}

/// /// \tparam genType floating point type -/// \param x The Hyperbolic Angle \f$\alpha\f$ +/// \param x The Hyperbolic Angle \math{\alpha} template constexpr genType sinh(genType x) { return ::sinh(x); @@ -323,11 +323,11 @@ constexpr genType sinh(genType x) { /// -/// \brief Returns the Hyperbolic Cosine Function, \f$\frac{{e}^{x}+{e}^{-x}}{2}\f$ +/// \brief Returns the Hyperbolic Cosine Function, \math{\frac{{e}^{x}+{e}^{-x}}{2}} /// -/// \returns The Hyperbolic Cosine of \f$x\f$, \f$\frac{{e}^{x}+{e}^{-x}}{2}\f$

+/// \returns The Hyperbolic Cosine of \math{x}, \math{\frac{{e}^{x}+{e}^{-x}}{2}}

/// -/// \param x The Hyperbolic Angle \f$\alpha\f$ +/// \param x The Hyperbolic Angle \math{\alpha} template constexpr genType cosh(genType x) { return ::cosh(x); @@ -335,11 +335,11 @@ constexpr genType cosh(genType x) { /// -/// \brief Returns the Hyperbolic Tangent Function, \f$\frac{\text{sinh}(x)}{\text{cosh}(x)}\f$ +/// \brief Returns the Hyperbolic Tangent Function, \math{\frac{\text{sinh}(x)}{\text{cosh}(x)}} /// -/// \returns The Hyperbolic Tangent of \f$x\f$, \f$\frac{{e}^{x}+{e}^{-x}}{2}\f$

+/// \returns The Hyperbolic Tangent of \math{x}, \math{\frac{{e}^{x}+{e}^{-x}}{2}}

/// -/// \param x The Hyperbolic Angle \f$\alpha\f$ +/// \param x The Hyperbolic Angle \math{\alpha} template constexpr genType tanh(genType x) { return ::tanh(x); @@ -355,10 +355,10 @@ constexpr genType tanh(genType x) { /// /// \brief The Inverse Hyperbolic Sine Function /// -/// \returns the value \f$y\f$ that fulfills \f$x=\text{sinh}(y)\f$

+/// \returns the value \math{y} that fulfills \math{x=\text{sinh}(y)}

/// \details The Inverse Hyperbolic Sine Function

/// -/// \param x the hyperbolic angle \f$\alpha\f$ +/// \param x the hyperbolic angle \math{\alpha} template constexpr genType asinh(genType x) { return ::asinh(x); @@ -368,10 +368,10 @@ constexpr genType asinh(genType x) { /// /// \brief The Inverse Hyperbolic Cosine Function /// -/// \returns the value \f$y\f$ that fulfills \f$x=\text{cosh}(y)\f$

+/// \returns the value \math{y} that fulfills \math{x=\text{cosh}(y)}

/// \details The Inverse Hyperbolic Cosine Function

/// -/// \param x the hyperbolic angle \f$\alpha\f$ +/// \param x the hyperbolic angle \math{\alpha} template constexpr genType acosh(genType x) { return ::acosh(x); @@ -381,10 +381,10 @@ constexpr genType acosh(genType x) { /// /// \brief The Inverse Hyperbolic Tangent Function /// -/// \returns the value \f$y\f$ that fulfills \f$x=\text{atanh}(y)\f$

+/// \returns the value \math{y} that fulfills \math{x=\text{atanh}(y)}

/// \details The Inverse Hyperbolic Tangent Function

/// -/// \param x The Hyperbolic Angle \f$\alpha\f$ +/// \param x The Hyperbolic Angle \math{\alpha} template constexpr genType atanh(genType x) { return ::atanh(x); diff --git a/include/fennec/math/vector.h b/include/fennec/math/vector.h index b638056..737c02a 100644 --- a/include/fennec/math/vector.h +++ b/include/fennec/math/vector.h @@ -46,33 +46,33 @@ /// ///
Type Corresponding Type Brief ///
Floats -///
``\f$vec2\f$`` \ref fennec::vec2 \copybrief fennec::vec2 -///
``\f$vec3\f$`` \ref fennec::vec3 \copybrief fennec::vec3 -///
``\f$vec4\f$`` \ref fennec::vec4 \copybrief fennec::vec4 +///
``\emph{vec2}`` \ref fennec::vec2 \copybrief fennec::vec2 +///
``\emph{vec3}`` \ref fennec::vec3 \copybrief fennec::vec3 +///
``\emph{vec4}`` \ref fennec::vec4 \copybrief fennec::vec4 ///
Doubles -///
``\f$dvec2\f$``\ref fennec::dvec2 \copybrief fennec::dvec2 -///
``\f$dvec3\f$``\ref fennec::dvec3 \copybrief fennec::dvec3 -///
``\f$dvec4\f$``\ref fennec::dvec4 \copybrief fennec::dvec4 +///
``\emph{dvec2}``\ref fennec::dvec2 \copybrief fennec::dvec2 +///
``\emph{dvec3}``\ref fennec::dvec3 \copybrief fennec::dvec3 +///
``\emph{dvec4}``\ref fennec::dvec4 \copybrief fennec::dvec4 ///
Booleans -///
``\f$bvec2\f$`` \ref fennec::bvec2 \copybrief fennec::bvec2 -///
``\f$bvec3\f$`` \ref fennec::bvec3 \copybrief fennec::bvec3 -///
``\f$bvec4\f$`` \ref fennec::bvec4 \copybrief fennec::bvec4 +///
``\emph{bvec2}`` \ref fennec::bvec2 \copybrief fennec::bvec2 +///
``\emph{bvec3}`` \ref fennec::bvec3 \copybrief fennec::bvec3 +///
``\emph{bvec4}`` \ref fennec::bvec4 \copybrief fennec::bvec4 ///
Integers -///
``\f$ivec2\f$`` \ref fennec::ivec2 \copybrief fennec::ivec2 -///
``\f$ivec3\f$`` \ref fennec::ivec3 \copybrief fennec::ivec3 -///
``\f$ivec4\f$`` \ref fennec::ivec4 \copybrief fennec::ivec4 +///
``\emph{ivec2}`` \ref fennec::ivec2 \copybrief fennec::ivec2 +///
``\emph{ivec3}`` \ref fennec::ivec3 \copybrief fennec::ivec3 +///
``\emph{ivec4}`` \ref fennec::ivec4 \copybrief fennec::ivec4 ///
Unsigned Integers -///
``\f$uvec2\f$`` \ref fennec::uvec2 \copybrief fennec::uvec2 -///
``\f$uvec3\f$`` \ref fennec::uvec3 \copybrief fennec::uvec3 -///
``\f$uvec4\f$`` \ref fennec::uvec4 \copybrief fennec::uvec4 +///
``\emph{uvec2}`` \ref fennec::uvec2 \copybrief fennec::uvec2 +///
``\emph{uvec3}`` \ref fennec::uvec3 \copybrief fennec::uvec3 +///
``\emph{uvec4}`` \ref fennec::uvec4 \copybrief fennec::uvec4 ///
/// /// /// /// \section vector_components Components /// -/// Vectors are usually made up of one to four components, named ``\f$x\f$``, ``\f$y\f$``, ``\f$z\f$``, and ``\f$w\f$``. -/// Each component also has aliases for usage in colors ``\f$rgba\f$``, and texture coordinates ``\f$stpq\f$``. Accessing a +/// Vectors are usually made up of one to four components, named \math{x}, \math{y}, \math{z}, and \math{w}. +/// Each component also has aliases for usage in colors \math{rgba}, and texture coordinates \math{stpq}. Accessing a /// component outside the vector will cause an error at compile time, for example: /// /// \code{.cpp} @@ -93,9 +93,9 @@ /// The fennec \ref fennec_math_vector allows for the "swizzling" of vectors. Each component in the vector can be /// used in any combination, with up to 4 components, to create another vector. For example,

/// -/// let \f$V = (0, 1, 2)\f$ -/// then \f$V.xy = (0, 1)\f$ -/// and \f$V.zy = (2, 1)\f$ +/// let \math{V = (0, 1, 2)} +/// then \math{V.xy = (0, 1)} +/// and \math{V.zy = (2, 1)} /// /// \section section_vectors_more More Info /// - \subpage fennec_math_vector_traits @@ -125,22 +125,22 @@ using vec = decltype(detail::_gen_vector(make_index_metasequenc /// -/// \brief Shorthand for creating a 2-element \ref fennec::vector, ```vec``` -/// \details Shorthand for creating a 2-element \ref fennec::vector, ```vec``` +/// \brief Shorthand for creating a 2-element \ref fennec::vector, `(.*?)` +/// \details Shorthand for creating a 2-element \ref fennec::vector, `(.*?)` /// \tparam ScalarT The type of the Components template using tvec2 = vec; /// -/// \brief Shorthand for creating a 3-element \ref fennec::vector, ```vec``` -/// \details Shorthand for creating a 3-element \ref fennec::vector, ```vec``` +/// \brief Shorthand for creating a 3-element \ref fennec::vector, `(.*?)` +/// \details Shorthand for creating a 3-element \ref fennec::vector, `(.*?)` /// \tparam ScalarT The type of the Components template using tvec3 = vec; /// -/// \brief Shorthand for creating a 4-element \ref fennec::vector, ```vec``` -/// \details Shorthand for creating a 4-element \ref fennec::vector, ```vec``` +/// \brief Shorthand for creating a 4-element \ref fennec::vector, `(.*?)` +/// \details Shorthand for creating a 4-element \ref fennec::vector, `(.*?)` /// \tparam ScalarT The type of the Components template using tvec4 = vec; @@ -377,7 +377,7 @@ struct vector : detail::vector_base_type /// \brief decay implementation /// /// \details - /// \returns scalar if \f$N==1\f$, otherwise, \ref fennec_math_vector "vector" + /// \returns scalar if \math{N==1}, otherwise, \ref fennec_math_vector "vector" decay_t decay() { return static_cast(*this); } @@ -418,7 +418,7 @@ struct vector : detail::vector_base_type /// \brief copy assignment /// /// \details - /// \returns A reference to \c this, after having set \p lhs, such that \f$lhs_i=rhs_i\f$ + /// \returns A reference to \c this, after having set \p lhs, such that \math{lhs_i=rhs_i} /// \param rhs vector to copy constexpr vector_t& operator=(const vector_t& rhs) { return ((data[IndicesV] = rhs[IndicesV]), ..., *this); @@ -428,7 +428,7 @@ struct vector : detail::vector_base_type /// \brief move assignment /// /// \details - /// \returns A reference to \c this, after having set \p lhs, such that \f$lhs_i=rhs_i\f$ + /// \returns A reference to \c this, after having set \p lhs, such that \math{lhs_i=rhs_i} /// \param rhs vector to move constexpr vector_t& operator=(vector_t&& rhs) noexcept { return ((data[IndicesV] = fennec::move(rhs[IndicesV])), ..., *this); @@ -474,7 +474,7 @@ struct vector : detail::vector_base_type /// \brief \ref fennec_math_scalar "scalar" - \ref fennec_math_vector "vector" addition operator /// /// \details - /// \returns A \ref fennec_math_vector "vector" \a v such that, \f$v_i=lhs_i+rhs_i\f$ + /// \returns A \ref fennec_math_vector "vector" \a v such that, \math{v_i=lhs_i+rhs_i} /// \param lhs left hand side /// \param rhs right hand side constexpr friend vector_t operator+(scalar_t lhs, const vector_t& rhs) { @@ -485,7 +485,7 @@ struct vector : detail::vector_base_type /// \brief \ref fennec_math_scalar "scalar" - \ref fennec_math_vector "vector" subtraction operator /// /// \details - /// \returns A \ref fennec_math_vector "vector" \a v such that, \f$v_i=lhs_i-rhs_i\f$ + /// \returns A \ref fennec_math_vector "vector" \a v such that, \math{v_i=lhs_i-rhs_i} /// \param lhs left hand side /// \param rhs right hand side constexpr friend vector_t operator-(scalar_t lhs, const vector_t& rhs) { @@ -496,7 +496,7 @@ struct vector : detail::vector_base_type /// \brief \ref fennec_math_scalar "scalar" - \ref fennec_math_vector "vector" multiplication operator /// /// \details - /// \returns A \ref fennec_math_vector "vector" \a v such that, \f$v_i={lhs_i}\cdot{rhs_i}\f$ + /// \returns A \ref fennec_math_vector "vector" \a v such that, \math{v_i={lhs_i}\cdot{rhs_i}} /// \param lhs left hand side /// \param rhs right hand side constexpr friend vector_t operator*(scalar_t lhs, const vector_t& rhs) { @@ -507,7 +507,7 @@ struct vector : detail::vector_base_type /// \brief \ref fennec_math_scalar "scalar" - \ref fennec_math_vector "vector" division operator /// /// \details - /// \returns A \ref fennec_math_vector "vector" \a v such that, \f$v_i=\frac{lhs_i}{rhs_i}\f$ + /// \returns A \ref fennec_math_vector "vector" \a v such that, \math{v_i=\frac{lhs_i}{rhs_i}} /// \param lhs left hand side /// \param rhs right hand side constexpr friend vector_t operator/(scalar_t lhs, const vector_t& rhs) { @@ -518,7 +518,7 @@ struct vector : detail::vector_base_type /// \brief \ref fennec_math_scalar "scalar" - \ref fennec_math_vector "vector" integer modulus operator /// /// \details - /// \returns A \ref fennec_math_vector "vector" \a v such that, \f$v_i=lhs_i\%rhs_i\f$ + /// \returns A \ref fennec_math_vector "vector" \a v such that, \math{v_i=lhs_i\%rhs_i} /// \param lhs left hand side /// \param rhs right hand side constexpr friend vector_t operator%(scalar_t lhs, const vector_t& rhs) requires(is_integral_v) { @@ -536,7 +536,7 @@ struct vector : detail::vector_base_type /// \brief \ref fennec_math_vector "vector" - \ref fennec_math_scalar "scalar" addition operator /// /// \details - /// \returns A \ref fennec_math_vector "vector" \a v such that, \f$v_i=lhs_i+rhs_i\f$ + /// \returns A \ref fennec_math_vector "vector" \a v such that, \math{v_i=lhs_i+rhs_i} /// \param lhs left hand side /// \param rhs right hand side constexpr friend vector_t operator+(const vector_t& lhs, scalar_t rhs) { @@ -549,7 +549,7 @@ struct vector : detail::vector_base_type /// \details /// \param lhs left hand side /// \param rhs right hand side - /// \returns A \ref fennec_math_vector "vector" \a v such that, \f$v_i=lhs_i-rhs_i\f$ + /// \returns A \ref fennec_math_vector "vector" \a v such that, \math{v_i=lhs_i-rhs_i} constexpr friend vector_t operator-(const vector_t& lhs, scalar_t rhs) { return vector_t((lhs[IndicesV] - rhs)...); } @@ -560,7 +560,7 @@ struct vector : detail::vector_base_type /// \details /// \param lhs left hand side /// \param rhs right hand side - /// \returns A \ref fennec_math_vector "vector" \a v such that, \f$v_i={lhs_i}\cdot{rhs_i}\f$ + /// \returns A \ref fennec_math_vector "vector" \a v such that, \math{v_i={lhs_i}\cdot{rhs_i}} constexpr friend vector_t operator*(const vector_t& lhs, scalar_t rhs) { return vector_t((lhs[IndicesV] * rhs)...); } @@ -571,7 +571,7 @@ struct vector : detail::vector_base_type /// \details /// \param lhs left hand side /// \param rhs right hand side - /// \returns A \ref fennec_math_vector "vector" \a v such that, \f$v_i=\frac{lhs_i}{rhs_i}\f$ + /// \returns A \ref fennec_math_vector "vector" \a v such that, \math{v_i=\frac{lhs_i}{rhs_i}} constexpr friend vector_t operator/(const vector_t& lhs, scalar_t rhs) { return vector((lhs[IndicesV] / rhs)...); } @@ -582,7 +582,7 @@ struct vector : detail::vector_base_type /// \details /// \param lhs left hand side /// \param rhs right hand side - /// \returns A \ref fennec_math_vector "vector" \a v such that, \f$v_i=lhs_i\%rhs_i\f$ + /// \returns A \ref fennec_math_vector "vector" \a v such that, \math{v_i=lhs_i\%rhs_i} constexpr friend vector_t operator%(const vector_t& lhs, scalar_t rhs) requires(is_integral_v) { return vector((lhs[IndicesV] % rhs)...); } @@ -600,7 +600,7 @@ struct vector : detail::vector_base_type /// \details /// \param lhs Left Hand Side of the Expression /// \param rhs Right Hand Side of the Expression - /// \returns A \ref fennec_math_vector "vector" \a v such that, \f$v_i=lhs_i+rhs_i\f$ + /// \returns A \ref fennec_math_vector "vector" \a v such that, \math{v_i=lhs_i+rhs_i} constexpr friend vector_t& operator+=(vector_t& lhs, scalar_t rhs) { return ((lhs[IndicesV] += rhs), ..., lhs); } @@ -611,7 +611,7 @@ struct vector : detail::vector_base_type /// \details /// \param lhs Left Hand Side of the Expression /// \param rhs Right Hand Side of the Expression - /// \returns A \ref fennec_math_vector "vector" \a v such that, \f$v_i=lhs_i-rhs_i\f$ + /// \returns A \ref fennec_math_vector "vector" \a v such that, \math{v_i=lhs_i-rhs_i} constexpr friend vector_t& operator-=(vector_t& lhs, scalar_t rhs) { return ((lhs[IndicesV] -= rhs), ..., lhs); } @@ -622,7 +622,7 @@ struct vector : detail::vector_base_type /// \details /// \param lhs Left Hand Side of the Expression /// \param rhs Right Hand Side of the Expression - /// \returns A \ref fennec_math_vector "vector" \a v such that, \f$v_i={lhs_i}\cdot{rhs_i}\f$ + /// \returns A \ref fennec_math_vector "vector" \a v such that, \math{v_i={lhs_i}\cdot{rhs_i}} constexpr friend vector_t& operator*=(vector_t& lhs, scalar_t rhs) { return ((lhs[IndicesV] *= rhs), ..., lhs); } @@ -633,7 +633,7 @@ struct vector : detail::vector_base_type /// \details /// \param lhs Left Hand Side of the Expression /// \param rhs Right Hand Side of the Expression - /// \returns A \ref fennec_math_vector "vector" \a v such that, \f$v_i=\frac{lhs_i}{rhs_i}\f$ + /// \returns A \ref fennec_math_vector "vector" \a v such that, \math{v_i=\frac{lhs_i}{rhs_i}} constexpr friend vector_t& operator/=(vector_t& lhs, scalar_t rhs) { return ((lhs[IndicesV] /= rhs), ..., lhs); } @@ -644,7 +644,7 @@ struct vector : detail::vector_base_type /// \details /// \param lhs Left Hand Side of the Expression /// \param rhs Right Hand Side of the Expression - /// \returns A \ref fennec_math_vector "vector" \a v such that, \f$v_i=lhs_i\%rhs_i\f$ + /// \returns A \ref fennec_math_vector "vector" \a v such that, \math{v_i=lhs_i\%rhs_i} constexpr friend vector_t& operator%=(vector_t& lhs, scalar_t rhs) requires(is_integral_v) { return ((lhs[IndicesV] %= rhs), ..., lhs); } @@ -661,7 +661,7 @@ struct vector : detail::vector_base_type /// /// \details /// \param x the vector - /// \returns A \ref fennec_math_vector "vector" \a v such that, \f$v_i=-x_i\f$ + /// \returns A \ref fennec_math_vector "vector" \a v such that, \math{v_i=-x_i} constexpr friend vector_t operator-(const vector_t& x) { return vector((-x[IndicesV])...); } @@ -672,7 +672,7 @@ struct vector : detail::vector_base_type /// \details /// \param lhs Left Hand Side of the Expression /// \param rhs Right Hand Side of the Expression - /// \returns A \ref fennec_math_vector "vector" \a v such that, \f$v_i=lhs_i+rhs_i\f$ + /// \returns A \ref fennec_math_vector "vector" \a v such that, \math{v_i=lhs_i+rhs_i} constexpr friend vector_t operator+(const vector_t& lhs, const vector_t& rhs) { return vector((lhs[IndicesV] + rhs[IndicesV])...); } @@ -683,7 +683,7 @@ struct vector : detail::vector_base_type /// \details /// \param lhs Left Hand Side of the Expression /// \param rhs Right Hand Side of the Expression - /// \returns A \ref fennec_math_vector "vector" \a v such that, \f$v_i=lhs_i-rhs_i\f$ + /// \returns A \ref fennec_math_vector "vector" \a v such that, \math{v_i=lhs_i-rhs_i} constexpr friend vector_t operator-(const vector_t& lhs, const vector_t& rhs) { return vector((lhs[IndicesV] - rhs[IndicesV])...); } @@ -694,7 +694,7 @@ struct vector : detail::vector_base_type /// \details /// \param lhs Left Hand Side of the Expression /// \param rhs Right Hand Side of the Expression - /// \returns A \ref fennec_math_vector "vector" \a v such that, \f$v_i={lhs_i}\cdot{rhs_i}\f$ + /// \returns A \ref fennec_math_vector "vector" \a v such that, \math{v_i={lhs_i}\cdot{rhs_i}} constexpr friend vector_t operator*(const vector_t& lhs, const vector_t& rhs) { return vector((lhs[IndicesV] * rhs[IndicesV])...); } @@ -703,7 +703,7 @@ struct vector : detail::vector_base_type /// \brief \ref fennec_math_vector "vector" - \ref fennec_math_vector "vector" division operator /// \param lhs Left Hand Side of the Expression /// \param rhs Right Hand Side of the Expression - /// \returns A \ref fennec_math_vector "vector" \a v such that, \f$v_i=\frac{lhs_i}{rhs_i}\f$ + /// \returns A \ref fennec_math_vector "vector" \a v such that, \math{v_i=\frac{lhs_i}{rhs_i}} constexpr friend vector_t operator/(const vector_t& lhs, const vector_t& rhs) { return vector((lhs[IndicesV] / rhs[IndicesV])...); } @@ -714,7 +714,7 @@ struct vector : detail::vector_base_type /// \details /// \param lhs Left Hand Side of the Expression /// \param rhs Right Hand Side of the Expression - /// \returns A \ref fennec_math_vector "vector" \a v such that, \f$v_i=lhs_i\%rhs_i\f$ + /// \returns A \ref fennec_math_vector "vector" \a v such that, \math{v_i=lhs_i\%rhs_i} constexpr friend vector_t operator%(const vector_t& lhs, const vector_t& rhs) requires(is_integral_v) { return vector((lhs[IndicesV] % rhs[IndicesV])...); } @@ -732,7 +732,7 @@ struct vector : detail::vector_base_type /// \details /// \param lhs Left Hand Side of the Expression /// \param rhs Right Hand Side of the Expression - /// \returns A \ref fennec_math_vector "vector" \a v such that, \f$v_i=lhs_i+rhs_i\f$ + /// \returns A \ref fennec_math_vector "vector" \a v such that, \math{v_i=lhs_i+rhs_i} constexpr friend vector_t& operator+=(vector_t& lhs, const vector_t& rhs) { return ((lhs[IndicesV] += rhs[IndicesV]), ..., lhs); } @@ -743,7 +743,7 @@ struct vector : detail::vector_base_type /// \details /// \param lhs Left Hand Side of the Expression /// \param rhs Right Hand Side of the Expression - /// \returns A \ref fennec_math_vector "vector" \a v such that, \f$v_i=lhs_i-rhs_i\f$ + /// \returns A \ref fennec_math_vector "vector" \a v such that, \math{v_i=lhs_i-rhs_i} constexpr friend vector_t& operator-=(vector_t& lhs, const vector_t& rhs) { return ((lhs[IndicesV] -= rhs[IndicesV]), ..., lhs); } @@ -754,7 +754,7 @@ struct vector : detail::vector_base_type /// \details /// \param lhs Left Hand Side of the Expression /// \param rhs Right Hand Side of the Expression - /// \returns A \ref fennec_math_vector "vector" \a v such that, \f$v_i={lhs_i}\cdot{rhs_i}\f$ + /// \returns A \ref fennec_math_vector "vector" \a v such that, \math{v_i={lhs_i}\cdot{rhs_i}} constexpr friend vector_t& operator*=(vector_t& lhs, const vector_t& rhs) { return ((lhs[IndicesV] *= rhs[IndicesV]), ..., lhs); } @@ -765,7 +765,7 @@ struct vector : detail::vector_base_type /// \details /// \param lhs Left Hand Side of the Expression /// \param rhs Right Hand Side of the Expression - /// \returns A \ref fennec_math_vector "vector" \a v such that, \f$v_i=\frac{lhs_i}{rhs_i}\f$ + /// \returns A \ref fennec_math_vector "vector" \a v such that, \math{v_i=\frac{lhs_i}{rhs_i}} constexpr friend vector_t& operator/=(vector_t& lhs, const vector_t& rhs) { return ((lhs[IndicesV] /= rhs[IndicesV]), ..., lhs); } @@ -776,7 +776,7 @@ struct vector : detail::vector_base_type /// \details /// \param lhs Left Hand Side of the Expression /// \param rhs Right Hand Side of the Expression - /// \returns A \ref fennec_math_vector "vector" \a v such that, \f$v_i=lhs_i\%rhs_i\f$ + /// \returns A \ref fennec_math_vector "vector" \a v such that, \math{v_i=lhs_i\%rhs_i} constexpr friend vector_t& operator%=(vector_t& lhs, const vector_t& rhs) requires(is_integral_v) { return ((lhs[IndicesV] %= rhs[IndicesV]), ..., lhs); } @@ -793,7 +793,7 @@ struct vector : detail::vector_base_type /// /// \details /// \param x the vector - /// \returns A \ref fennec_math_vector "vector" \a v such that, \f$v_i=!x_i\f$ + /// \returns A \ref fennec_math_vector "vector" \a v such that, \math{v_i=!x_i} constexpr friend vector_t operator!(const vector_t& x) { return vector_t(!x[IndicesV]...); } @@ -804,7 +804,7 @@ struct vector : detail::vector_base_type /// \details /// \param lhs Left Hand Side of the Expression /// \param rhs Right Hand Side of the Expression - /// \returns A \ref fennec_math_vector "vector" \a v such that, \f$v_i=lhs_i\&\&rhs_i\f$ + /// \returns A \ref fennec_math_vector "vector" \a v such that, \math{v_i=lhs_i\&\&rhs_i} constexpr friend vector_t operator&&(const vector_t& lhs, scalar_t rhs) requires(is_bool_v) { return vector_t((lhs[IndicesV] && rhs)...); } @@ -813,7 +813,7 @@ struct vector : detail::vector_base_type /// \brief \ref fennec_math_vector "vector" - \ref fennec_math_vector "vector" logical and operator /// \param lhs Left Hand Side of the Expression /// \param rhs Right Hand Side of the Expression - /// \returns A \ref fennec_math_vector "vector" \a v such that, \f$v_i=lhs_i\&\&rhs_i\f$ + /// \returns A \ref fennec_math_vector "vector" \a v such that, \math{v_i=lhs_i\&\&rhs_i} constexpr friend vector_t operator&&(const vector_t& lhs, const vector_t& rhs) requires(is_bool_v) { return vector_t((lhs[IndicesV] && rhs[IndicesV])...); } @@ -824,7 +824,7 @@ struct vector : detail::vector_base_type /// \details /// \param lhs Left Hand Side of the Expression /// \param rhs Right Hand Side of the Expression - /// \returns A \ref fennec_math_vector "vector" \a v such that, \f$v_i=lhs_i\|\|rhs_i\f$ + /// \returns A \ref fennec_math_vector "vector" \a v such that, \math{v_i=lhs_i\|\|rhs_i} constexpr friend vector_t operator||(const vector_t& lhs, scalar_t rhs) requires(is_bool_v) { return vector_t((lhs[IndicesV] || rhs)...); } @@ -835,7 +835,7 @@ struct vector : detail::vector_base_type /// \details /// \param lhs Left Hand Side of the Expression /// \param rhs Right Hand Side of the Expression - /// \returns A \ref fennec_math_vector "vector" \a v such that, \f$v_i=lhs_i\|\|rhs_i\f$ + /// \returns A \ref fennec_math_vector "vector" \a v such that, \math{v_i=lhs_i\|\|rhs_i} constexpr friend vector_t operator||(const vector_t& lhs, const vector_t& rhs) requires(is_bool_v) { return vector_t((lhs[IndicesV] || rhs[IndicesV])...); } @@ -853,7 +853,7 @@ struct vector : detail::vector_base_type /// \details /// \param lhs Left Hand Side of the Expression /// \param rhs Right Hand Side of the Expression - /// \returns A \ref fennec_math_vector "vector" \a v such that, \f$v_i=lhs_i\&rhs_i\f$ + /// \returns A \ref fennec_math_vector "vector" \a v such that, \math{v_i=lhs_i\&rhs_i} constexpr friend vector_t operator&(scalar_t rhs, const vector_t& lhs) requires(is_integral_v) { return vector_t((lhs[IndicesV] & rhs)...); } @@ -864,7 +864,7 @@ struct vector : detail::vector_base_type /// \details /// \param lhs Left Hand Side of the Expression /// \param rhs Right Hand Side of the Expression - /// \returns A \ref fennec_math_vector "vector" \a v such that, \f$v_i=lhs_i\&rhs_i\f$ + /// \returns A \ref fennec_math_vector "vector" \a v such that, \math{v_i=lhs_i\&rhs_i} constexpr friend vector_t operator&(const vector_t& lhs, scalar_t rhs) requires(is_integral_v) { return vector_t((lhs[IndicesV] & rhs)...); } @@ -875,7 +875,7 @@ struct vector : detail::vector_base_type /// \details /// \param lhs Left Hand Side of the Expression /// \param rhs Right Hand Side of the Expression - /// \returns A \ref fennec_math_vector "vector" \a v such that, \f$v_i=lhs_i\&rhs_i\f$ + /// \returns A \ref fennec_math_vector "vector" \a v such that, \math{v_i=lhs_i\&rhs_i} constexpr friend vector_t operator&=(vector_t& lhs, scalar_t rhs) requires(is_integral_v) { return ((lhs[IndicesV] &= rhs), ..., lhs); } @@ -886,7 +886,7 @@ struct vector : detail::vector_base_type /// \details /// \param lhs Left Hand Side of the Expression /// \param rhs Right Hand Side of the Expression - /// \returns A \ref fennec_math_vector "vector" \a v such that, \f$v_i=lhs_i\&rhs_i\f$ + /// \returns A \ref fennec_math_vector "vector" \a v such that, \math{v_i=lhs_i\&rhs_i} constexpr friend vector_t operator&(const vector_t& lhs, const vector_t& rhs) requires(is_integral_v< scalar_t>) { return vector_t((lhs[IndicesV] & rhs[IndicesV])...); @@ -898,7 +898,7 @@ struct vector : detail::vector_base_type /// \details /// \param lhs Left Hand Side of the Expression /// \param rhs Right Hand Side of the Expression - /// \returns A \ref fennec_math_vector "vector" \a v such that, \f$v_i=lhs_i\&rhs_i\f$ + /// \returns A \ref fennec_math_vector "vector" \a v such that, \math{v_i=lhs_i\&rhs_i} constexpr friend vector_t operator&=(vector_t& lhs, const vector_t& rhs) requires(is_integral_v) { return ((lhs[IndicesV] &= rhs[IndicesV]), ..., lhs); } @@ -910,7 +910,7 @@ struct vector : detail::vector_base_type /// \details /// \param lhs Left Hand Side of the Expression /// \param rhs Right Hand Side of the Expression - /// \returns A \ref fennec_math_vector "vector" \a v such that, \f$v_i=lhs_i|rhs_i\f$ + /// \returns A \ref fennec_math_vector "vector" \a v such that, \math{v_i=lhs_i|rhs_i} constexpr friend vector_t operator|(scalar_t rhs, const vector_t& lhs) requires(is_integral_v) { return vector_t((lhs[IndicesV] | rhs)...); } @@ -921,7 +921,7 @@ struct vector : detail::vector_base_type /// \details /// \param lhs Left Hand Side of the Expression /// \param rhs Right Hand Side of the Expression - /// \returns A \ref fennec_math_vector "vector" \a v such that, \f$v_i=lhs_i|rhs_i\f$ + /// \returns A \ref fennec_math_vector "vector" \a v such that, \math{v_i=lhs_i|rhs_i} constexpr friend vector_t operator|(const vector_t& lhs, scalar_t rhs) requires(is_integral_v) { return vector_t((lhs[IndicesV] | rhs)...); } @@ -932,7 +932,7 @@ struct vector : detail::vector_base_type /// \details /// \param lhs Left Hand Side of the Expression /// \param rhs Right Hand Side of the Expression - /// \returns A \ref fennec_math_vector "vector" \a v such that, \f$v_i=lhs_i|rhs_i\f$ + /// \returns A \ref fennec_math_vector "vector" \a v such that, \math{v_i=lhs_i|rhs_i} constexpr friend vector_t operator|=(vector_t& lhs, scalar_t rhs) requires(is_integral_v) { return ((lhs[IndicesV] |= rhs), ..., lhs); } @@ -943,7 +943,7 @@ struct vector : detail::vector_base_type /// \details /// \param lhs Left Hand Side of the Expression /// \param rhs Right Hand Side of the Expression - /// \returns A \ref fennec_math_vector "vector" \a v such that, \f$v_i=lhs_i|rhs_i\f$ + /// \returns A \ref fennec_math_vector "vector" \a v such that, \math{v_i=lhs_i|rhs_i} constexpr friend vector_t operator|(const vector_t& lhs, const vector_t& rhs) requires(is_integral_v< scalar_t>) { return vector_t((lhs[IndicesV] | rhs[IndicesV])...); @@ -955,7 +955,7 @@ struct vector : detail::vector_base_type /// \details /// \param lhs Left Hand Side of the Expression /// \param rhs Right Hand Side of the Expression - /// \returns A \ref fennec_math_vector "vector" \a v such that, \f$v_i=lhs_i|rhs_i\f$ + /// \returns A \ref fennec_math_vector "vector" \a v such that, \math{v_i=lhs_i|rhs_i} constexpr friend vector_t operator|=(vector_t& lhs, const vector_t& rhs) requires(is_integral_v) { return ((lhs[IndicesV] |= rhs[IndicesV]), ..., lhs); } @@ -965,7 +965,7 @@ struct vector : detail::vector_base_type /// \ref fennec_math_scalar "scalar" - \ref fennec_math_vector "vector" bitwise xor operator /// \param lhs Left Hand Side of the Expression /// \param rhs Right Hand Side of the Expression - /// \returns A \ref fennec_math_vector "vector" \a v such that, \f$v_i=lhs_i\^rhs_i\f$ + /// \returns A \ref fennec_math_vector "vector" \a v such that, \math{v_i=lhs_i\^rhs_i} constexpr friend vector_t operator^(scalar_t lhs, const vector_t& rhs) requires(is_integral_v) { return vector_t((lhs ^ rhs[IndicesV])...); } @@ -974,7 +974,7 @@ struct vector : detail::vector_base_type /// \ref fennec_math_vector "vector" - \ref fennec_math_scalar "scalar" bitwise xor operator /// \param lhs Left Hand Side of the Expression /// \param rhs Right Hand Side of the Expression - /// \returns A \ref fennec_math_vector "vector" \a v such that, \f$v_i=lhs_i\^rhs_i\f$ + /// \returns A \ref fennec_math_vector "vector" \a v such that, \math{v_i=lhs_i\^rhs_i} constexpr friend vector_t operator^(const vector_t& lhs, scalar_t rhs) requires(is_integral_v) { return vector_t((lhs[IndicesV] ^ rhs)...); } @@ -983,7 +983,7 @@ struct vector : detail::vector_base_type /// \ref fennec_math_vector "vector" - \ref fennec_math_scalar "scalar" bitwise xor assignment operator /// \param lhs Left Hand Side of the Expression /// \param rhs Right Hand Side of the Expression - /// \returns A \ref fennec_math_vector "vector" \a v such that, \f$v_i=lhs_i\^rhs_i\f$ + /// \returns A \ref fennec_math_vector "vector" \a v such that, \math{v_i=lhs_i\^rhs_i} constexpr friend vector_t operator^=(vector_t& lhs, scalar_t rhs) requires(is_integral_v) { return ((lhs[IndicesV] ^= rhs), ..., lhs); } @@ -992,7 +992,7 @@ struct vector : detail::vector_base_type /// \ref fennec_math_vector "vector" - \ref fennec_math_vector "vector" bitwise xor operator /// \param lhs Left Hand Side of the Expression /// \param rhs Right Hand Side of the Expression - /// \returns A \ref fennec_math_vector "vector" \a v such that, \f$v_i=lhs_i\^rhs_i\f$ + /// \returns A \ref fennec_math_vector "vector" \a v such that, \math{v_i=lhs_i\^rhs_i} constexpr friend vector_t operator^(const vector_t& lhs, const vector_t& rhs) requires(is_integral_v< scalar_t>) { return vector_t((lhs[IndicesV] ^ rhs[IndicesV])...); @@ -1002,7 +1002,7 @@ struct vector : detail::vector_base_type /// \ref fennec_math_vector "vector" - \ref fennec_math_vector "vector" bitwise xor assignment operator /// \param lhs Left Hand Side of the Expression /// \param rhs Right Hand Side of the Expression - /// \returns A \ref fennec_math_vector "vector" \a v such that, \f$v_i=lhs_i\^rhs_i\f$ + /// \returns A \ref fennec_math_vector "vector" \a v such that, \math{v_i=lhs_i\^rhs_i} constexpr friend vector_t operator^=(vector_t& lhs, const vector_t& rhs) requires(is_integral_v) { return ((lhs[IndicesV] ^= rhs[IndicesV]), ..., lhs); } @@ -1012,7 +1012,7 @@ struct vector : detail::vector_base_type /// \ref fennec_math_scalar "scalar" - \ref fennec_math_vector "vector" bitwise left-shift operator /// \param lhs Left Hand Side of the Expression /// \param rhs Right Hand Side of the Expression - /// \returns A \ref fennec_math_vector "vector" \a v such that, \f$v_i=lhs_i<) { return vector_t((lhs << rhs[IndicesV])...); } @@ -1021,7 +1021,7 @@ struct vector : detail::vector_base_type /// \ref fennec_math_vector "vector" - \ref fennec_math_scalar "scalar" bitwise left-shift operator /// \param lhs Left Hand Side of the Expression /// \param rhs Right Hand Side of the Expression - /// \returns A \ref fennec_math_vector "vector" \a v such that, \f$v_i=lhs_i<) { return vector_t((lhs[IndicesV] << rhs)...); } @@ -1030,7 +1030,7 @@ struct vector : detail::vector_base_type /// \ref fennec_math_vector "vector" - \ref fennec_math_scalar "scalar" bitwise left-shift assignment operator /// \param lhs Left Hand Side of the Expression /// \param rhs Right Hand Side of the Expression - /// \returns A \ref fennec_math_vector "vector" \a v such that, \f$v_i=lhs_i<<=rhs_i\f$ + /// \returns A \ref fennec_math_vector "vector" \a v such that, \math{v_i=lhs_i<<=rhs_i} constexpr friend vector_t operator<<=(vector_t& lhs, scalar_t rhs) requires(is_integral_v) { return ((lhs[IndicesV] <<= rhs), ..., lhs); } @@ -1039,7 +1039,7 @@ struct vector : detail::vector_base_type /// \ref fennec_math_vector "vector" - \ref fennec_math_vector "vector" bitwise or operator /// \param lhs Left Hand Side of the Expression /// \param rhs Right Hand Side of the Expression - /// \returns A \ref fennec_math_vector "vector" \a v such that, \f$v_i=lhs_i<) { return vector_t((lhs[IndicesV] << rhs[IndicesV])...); } @@ -1048,7 +1048,7 @@ struct vector : detail::vector_base_type /// \ref fennec_math_vector "vector" - \ref fennec_math_vector "vector" bitwise or assignment operator /// \param lhs Left Hand Side of the Expression /// \param rhs Right Hand Side of the Expression - /// \returns A \ref fennec_math_vector "vector" \a v such that, \f$v_i=lhs_i<<=rhs_i\f$ + /// \returns A \ref fennec_math_vector "vector" \a v such that, \math{v_i=lhs_i<<=rhs_i} constexpr friend vector_t operator<<=(vector_t& lhs, const vector_t& rhs) requires(is_integral_v) { return ((lhs[IndicesV] <<= rhs[IndicesV]), ..., lhs); } @@ -1058,7 +1058,7 @@ struct vector : detail::vector_base_type /// \ref fennec_math_scalar "scalar" - \ref fennec_math_vector "vector" bitwise or operator /// \param lhs Left Hand Side of the Expression /// \param rhs Right Hand Side of the Expression - /// \returns A \ref fennec_math_vector "vector" \a v such that, \f$v_i=lhs_i>>rhs_i\f$ + /// \returns A \ref fennec_math_vector "vector" \a v such that, \math{v_i=lhs_i>>rhs_i} constexpr friend vector_t operator>>(scalar_t lhs, const vector_t& rhs) requires(is_integral_v) { return vector_t((lhs >> rhs[IndicesV])...); } @@ -1067,7 +1067,7 @@ struct vector : detail::vector_base_type /// \ref fennec_math_vector "vector" - \ref fennec_math_scalar "scalar" bitwise or operator /// \param lhs Left Hand Side of the Expression /// \param rhs Right Hand Side of the Expression - /// \returns A \ref fennec_math_vector "vector" \a v such that, \f$v_i=lhs_i>>rhs_i\f$ + /// \returns A \ref fennec_math_vector "vector" \a v such that, \math{v_i=lhs_i>>rhs_i} constexpr friend vector_t operator>>(const vector_t& lhs, scalar_t rhs) requires(is_integral_v) { return vector_t((lhs[IndicesV] >> rhs)...); } @@ -1076,7 +1076,7 @@ struct vector : detail::vector_base_type /// \ref fennec_math_vector "vector" - \ref fennec_math_scalar "scalar" bitwise left-shift assignment operator /// \param lhs Left Hand Side of the Expression /// \param rhs Right Hand Side of the Expression - /// \returns A \ref fennec_math_vector "vector" \a v such that, \f$v_i=lhs_i>>=rhs_i\f$ + /// \returns A \ref fennec_math_vector "vector" \a v such that, \math{v_i=lhs_i>>=rhs_i} constexpr friend vector_t operator>>=(vector_t& lhs, scalar_t rhs) requires(is_integral_v) { return ((lhs[IndicesV] >>= rhs), ..., lhs); } @@ -1085,7 +1085,7 @@ struct vector : detail::vector_base_type /// \ref fennec_math_vector "vector" - \ref fennec_math_vector "vector" bitwise or operator /// \param lhs Left Hand Side of the Expression /// \param rhs Right Hand Side of the Expression - /// \returns A \ref fennec_math_vector "vector" \a v such that, \f$v_i=lhs_i>>rhs_i\f$ + /// \returns A \ref fennec_math_vector "vector" \a v such that, \math{v_i=lhs_i>>rhs_i} constexpr friend vector_t operator>>(const vector_t& lhs, const vector_t& rhs) requires(is_integral_v) { return vector_t((lhs[IndicesV] >> rhs[IndicesV])...); } @@ -1094,7 +1094,7 @@ struct vector : detail::vector_base_type /// \ref fennec_math_vector "vector" - \ref fennec_math_vector "vector" bitwise or assignment operator /// \param lhs Left Hand Side of the Expression /// \param rhs Right Hand Side of the Expression - /// \returns A \ref fennec_math_vector "vector" \a v such that, \f$v_i=lhs_i>>=rhs_i\f$ + /// \returns A \ref fennec_math_vector "vector" \a v such that, \math{v_i=lhs_i>>=rhs_i} constexpr friend vector_t operator>>=(vector_t& lhs, const vector_t& rhs) requires(is_integral_v) { return ((lhs[IndicesV] >>= rhs[IndicesV]), ..., lhs); } diff --git a/include/fennec/math/vector_storage.h b/include/fennec/math/vector_storage.h index b18954e..5d24e53 100644 --- a/include/fennec/math/vector_storage.h +++ b/include/fennec/math/vector_storage.h @@ -25,6 +25,12 @@ #pragma GCC diagnostic ignored "-Wpedantic" #endif +#if FENNEC_COMPILER_CLANG +#pragma clang diagnostic push +#pragma clang diagnostic ignored "-Wgnu-anonymous-struct" +#pragma clang diagnostic ignored "-Wnested-anon-types" +#endif + #if FENNEC_COMPILER_MSVC #pragma warning(push) #pragma warning(disable:4201) @@ -617,4 +623,12 @@ namespace fennec::detail #pragma GCC diagnostic pop #endif +#ifdef FENNEC_COMPILER_CLANG +#pragma clang diagnostic pop +#endif + +#if FENNEC_COMPILER_MSVC +#pragma warning(pop) +#endif + #endif // FENNEC_MATH_VECTOR_STORAGE_H diff --git a/include/fennec/math/vector_traits.h b/include/fennec/math/vector_traits.h index 22f6268..47b0e96 100644 --- a/include/fennec/math/vector_traits.h +++ b/include/fennec/math/vector_traits.h @@ -74,17 +74,17 @@ namespace fennec template struct is_vector : detail::_is_vector_helper>{}; /// -/// \brief shorthand for ```is_vector::value``` +/// \brief shorthand for `(.*?)` /// \tparam T type to check template constexpr bool is_vector_v = is_vector::value; /// -/// \brief Get the number of Components in \p T, returns 1 for types that pass ```is_arithmetic```, returns \ref vector::N for \ref vector "Vector" Types, and returns 0 for all other cases +/// \brief Get the number of Components in \p T, returns 1 for types that pass `(.*?)`, returns \ref vector::N for \ref vector "Vector" Types, and returns 0 for all other cases /// \tparam T type to check template struct component_count : detail::_component_count_helper>{}; /// -/// \brief shorthand for ```component_count::value``` +/// \brief shorthand for `(.*?)` /// \tparam T type to get the component count of template constexpr size_t component_count_v = component_count::value; @@ -97,7 +97,7 @@ template struct total_component_count : integral_constant struct total_component_count<> : integral_constant{}; /// -/// \brief shorthand for ```component_count::value``` +/// \brief shorthand for `(.*?)` /// \tparam Ts types to accumulate the count of template constexpr size_t total_component_count_v = total_component_count::value; diff --git a/include/fennec/memory/allocator.h b/include/fennec/memory/allocator.h index ed29331..f6c54a6 100644 --- a/include/fennec/memory/allocator.h +++ b/include/fennec/memory/allocator.h @@ -122,15 +122,10 @@ public: /// \brief Alias for the size of allocations. Will use `Alloc::size_t` if present using size_t = typename _size::type; - // TODO: Document propagation - using propagate_on_container_copy_assignment = detect_t; - using propagate_on_container_move_assignment = detect_t; - using propagate_on_container_swap = detect_t; - /// \brief Checks if this allocator type is always equal to another allocator of similar type using is_always_equal = detect_t; - /// \brief Rebinds the allocator type to produce an element type of type \f$TypeT\f$ + /// \brief Rebinds the allocator type to produce an element type of type \emph{TypeT} template using rebind = typename _rebind::type; // TODO: allocator_traits static functions @@ -138,7 +133,7 @@ public: /// -/// \brief Allocator implementation, uses \f$new\f$ and \f$delete\f$ operators. +/// \brief Allocator implementation, uses \emph{new} and \emph{delete} operators. /// \tparam T The data type to allocate template class allocator @@ -166,39 +161,39 @@ public: /// /// \brief Copy Assignment - /// \returns A reference to self + /// \returns A reference to \emph{this} constexpr allocator& operator=(const allocator&) = default; /// /// \brief Equality operator - /// \returns \f$true\f$ + /// \returns \emph{true} constexpr bool_t operator==(const allocator&) { return true; } /// /// \brief Inequality operator - /// \returns \f$false\f$ + /// \returns \emph{false} constexpr bool_t operator!=(const allocator&) { return false; } /// /// \brief Equality operator for allocators of same type but with different data type - /// \returns \f$false\f$ + /// \returns \emph{false} template constexpr bool_t operator==(const allocator&) { return false; } /// /// \brief Inequality operator for allocators of same type but with different data type - /// \returns \f$true\f$ + /// \returns \emph{true} template constexpr bool_t operator!=(const allocator&) { return true; } /// - /// \brief Allocate a block of memory large enough to hold \f$n\f$ elements of type \f$T\f$ + /// \brief Allocate a block of memory large enough to hold \emph{n} elements of type \emph{T} /// \param n The number of elements /// \returns A pointer to the allocated block constexpr T* allocate(size_t n) { @@ -206,7 +201,7 @@ public: } /// - /// \brief Allocate a block of memory large enough to hold \f$n\f$ elements of type \f$T\f$ + /// \brief Allocate a block of memory large enough to hold \emph{n} elements of type \emph{T} /// \param n The number of elements /// \param align The alignment /// \returns A pointer to the allocated block @@ -215,14 +210,14 @@ public: } /// - /// \brief Deallocate a block of memory with type \f$T\f$ + /// \brief Deallocate a block of memory with type \emph{T} /// \param ptr The block to release constexpr void deallocate(T* ptr) { return ::operator delete(ptr); } /// - /// \brief Deallocate a block of memory with type \f$T\f$ + /// \brief Deallocate a block of memory with type \emph{T} /// \param ptr The block to release /// \param align The alignment constexpr void deallocate(T* ptr, align_t align) { @@ -232,7 +227,7 @@ public: /// -/// \brief Allocator implementation, uses \f$new\f$ and \f$delete\f$ operators. +/// \brief Allocator implementation, uses \emph{new} and \emph{delete} operators. /// \tparam T The data type to allocate template class allocator @@ -260,40 +255,40 @@ public: /// /// \brief Copy Assignment - /// \returns A reference to self + /// \returns A reference to \emph{this} constexpr allocator& operator=(const allocator&) = default; /// /// \brief Equality operator - /// \returns \f$true\f$ + /// \returns \emph{true} constexpr bool_t operator==(const allocator&) { return true; } /// /// \brief Inequality operator - /// \returns \f$false\f$ + /// \returns \emph{false} constexpr bool_t operator!=(const allocator&) { return false; } /// /// \brief Equality operator for allocators of same type but with different data type - /// \returns \f$false\f$ + /// \returns \emph{false} template constexpr bool_t operator==(const allocator&) { return false; } /// /// \brief Inequality operator for allocators of same type but with different data type - /// \returns \f$true\f$ + /// \returns \emph{true} template constexpr bool_t operator!=(const allocator&) { return true; } /// - /// \brief Allocate a block of memory large enough to hold \f$n\f$ elements of type \f$T\f$ + /// \brief Allocate a block of memory large enough to hold \emph{n} elements of type \emph{T} /// \param n The number of elements /// \returns A pointer to the allocated block constexpr T* allocate(size_t n) { @@ -301,7 +296,7 @@ public: } /// - /// \brief Allocate a block of memory large enough to hold \f$n\f$ elements of type \f$T\f$ + /// \brief Allocate a block of memory large enough to hold \emph{n} elements of type \emph{T} /// \param n The number of elements /// \param align The alignment /// \returns A pointer to the allocated block @@ -310,14 +305,14 @@ public: } /// - /// \brief Deallocate a block of memory with type \f$T\f$ + /// \brief Deallocate a block of memory with type \emph{T} /// \param ptr The block to release constexpr void deallocate(T* ptr) { return ::operator delete[](ptr); } /// - /// \brief Deallocate a block of memory with type \f$T\f$ + /// \brief Deallocate a block of memory with type \emph{T} /// \param ptr The block to release /// \param align The alignment constexpr void deallocate(T* ptr, align_t align) { @@ -364,14 +359,14 @@ public: /// @{ /// - /// \brief Default Constructor, initializes internal data to \f$null\f$ and the capacity to \f$0\f$ + /// \brief Default Constructor, initializes internal data to \emph{null} and the capacity to \emph{0} constexpr allocation() noexcept : _data(nullptr), _capacity(0), _alignment(zero()) { } /// /// \brief Sized Constructor, initializes the allocation with a block of size `n * sizeof(T)` bytes - /// \param n The number of elements of type \f$T\f$ to allocate for + /// \param n The number of elements of type \emph{T} to allocate for explicit constexpr allocation(size_t n) noexcept : _data(nullptr), _capacity(0), _alignment(zero()) { allocate(n); @@ -389,7 +384,7 @@ public: /// /// \brief Sized Constructor, initializes the allocation with a block of size `n * sizeof(T)` bytes - /// \param n The number of elements of type \f$T\f$ to allocate for + /// \param n The number of elements of type \emph{T} to allocate for /// \param align The alignment of the allocation constexpr allocation(size_t n, align_t align) noexcept : _data(nullptr) @@ -413,7 +408,7 @@ public: /// \brief Allocator Constructor /// \param alloc The allocation object to copy. /// - /// \details This constructor should be used when the type \f$AllocT\f$ needs internal data. + /// \details This constructor should be used when the type \emph{AllocT} needs internal data. explicit constexpr allocation(const alloc_t& alloc) noexcept : _alloc(alloc) , _data(nullptr) @@ -423,10 +418,10 @@ public: /// /// \brief Sized Allocator Constructor - /// \param n The number of elements of type \f$T\f$ to allocate for + /// \param n The number of elements of type \emph{T} to allocate for /// \param alloc The allocation object to copy. /// - /// \details This constructor should be used when the type \f$AllocT\f$ needs internal data. + /// \details This constructor should be used when the type \emph{AllocT} needs internal data. constexpr allocation(size_t n, const alloc_t& alloc) noexcept : _alloc(alloc) , _data(nullptr) @@ -442,7 +437,7 @@ public: /// \param n the number of elements /// \param alloc The allocation object to copy. /// - /// \details This constructor should be used when the type \f$AllocT\f$ needs internal data. + /// \details This constructor should be used when the type \emph{AllocT} needs internal data. constexpr allocation(const T* data, size_t n, const alloc_t& alloc) : allocation(n, alloc) { fennec::memmove(static_cast(_data), data, n); @@ -450,11 +445,11 @@ public: /// /// \brief Sized Allocator Constructor - /// \param n The number of elements of type \f$T\f$ to allocate for + /// \param n The number of elements of type \emph{T} to allocate for /// \param align The alignment of the allocation /// \param alloc The allocation object to copy. /// - /// \details This constructor should be used when the type \f$AllocT\f$ needs internal data. + /// \details This constructor should be used when the type \emph{AllocT} needs internal data. constexpr allocation(size_t n, align_t align, const alloc_t& alloc) noexcept : _alloc(alloc) , _data(nullptr) @@ -471,7 +466,7 @@ public: /// \param align The alignment of the allocation /// \param alloc The allocation object to copy. /// - /// \details This constructor should be used when the type \f$AllocT\f$ needs internal data. + /// \details This constructor should be used when the type \emph{AllocT} needs internal data. constexpr allocation(const T* data, size_t n, align_t align, const alloc_t& alloc) : allocation(n, align, alloc) { fennec::memmove(_data, data, n); @@ -489,7 +484,7 @@ public: } /// - /// \brief Move Constructor, moves the data in \f$alloc\f$ to the new object and cleans \f$alloc\f$ so that it + /// \brief Move Constructor, moves the data in \emph{alloc} to the new object and cleans \emph{alloc} so that it /// can safely destruct /// \param alloc The allocation to move constexpr allocation(allocation&& alloc) noexcept @@ -522,7 +517,7 @@ public: /// /// \brief Copy Assignment Operator /// \param alloc the allocation to copy - /// \returns a reference to \f$this\f$ + /// \returns a reference to \emph{this} constexpr allocation& operator=(const allocation& alloc) { allocation::allocate(alloc.capacity(), alloc.alignment()); fennec::memmove(_data, alloc, size()); @@ -532,7 +527,7 @@ public: /// /// \brief Move Assignment Operator /// \param alloc the allocation to copy - /// \returns a reference to \f$this\f$ + /// \returns a reference to \emph{this} constexpr allocation& operator=(allocation&& alloc) noexcept { // Copy contents @@ -561,7 +556,7 @@ public: } /// - /// \brief Getter for the number of elements \f$n\f$ of type \f$T\f$ that the allocation can hold. + /// \brief Getter for the number of elements \emph{n} of type \emph{T} that the allocation can hold. /// \returns the size of the allocation in elements constexpr size_t capacity() const { return _capacity; @@ -588,7 +583,7 @@ public: /// \details If there is already an allocated block of memory, the previous allocation is released. /// /// - /// \param n The number of elements of type \f$T\f$ to allocate for + /// \param n The number of elements of type \emph{T} to allocate for /// \param align The alignment to use constexpr void allocate(size_t n, align_t align = zero()) noexcept { deallocate(); @@ -620,7 +615,7 @@ public: /// \brief Reallocate the block with a new size. /// Contents are copied to the new allocation. /// - /// \param n The number of elements of type \f$T\f$ to allocate for + /// \param n The number of elements of type \emph{T} to allocate for /// \param align The alignment to use constexpr void reallocate(size_t n, align_t align = zero()) noexcept { if (_data == nullptr) { @@ -628,7 +623,8 @@ public: return; } - value_t* old = _data; size_t old_cap = _capacity; + value_t* old = _data; + const size_t old_cap = _capacity; _data = nullptr; allocate(n, align); @@ -655,7 +651,7 @@ public: /// /// \param i The index to access - /// \returns a reference to the value at position \f$i\f$ in the allocation + /// \returns a reference to the value at position \emph{i} in the allocation constexpr value_t& operator[](size_t i) { assertd(i < capacity(), "Array Out of Bounds"); return _data[i]; @@ -664,7 +660,7 @@ public: /// /// \brief Array Access Operator /// \param i The index to access - /// \returns a reference to the value at position \f$i\f$ in the allocation + /// \returns a reference to the value at position \emph{i} in the allocation constexpr const value_t& operator[](size_t i) const { assertd(i < capacity(), "Array Out of Bounds"); return _data[i]; diff --git a/include/fennec/memory/bytes.h b/include/fennec/memory/bytes.h index bc62b6e..347c4f4 100644 --- a/include/fennec/memory/bytes.h +++ b/include/fennec/memory/bytes.h @@ -89,27 +89,27 @@ public: /// /// \brief Array Access Operator /// \param i the index to access - /// \returns a reference to the byte at \f$i\f$ + /// \returns a reference to the byte at \emph{i} constexpr byte_t& operator[](int i) { assertd(not _const, "Attempted to Access Const-Qualified Memory as Non-Const"); - assertd(i >= 0 && (size_t)i < _size, "Array Out of Bounds"); + assertd(i >= 0 && size_t(i) < _size, "Array Out of Bounds"); return _arr[i]; } /// /// \brief Const Array Access Operator /// \param i the index to access - /// \returns a copy of the byte at \f$i\f$ + /// \returns a copy of the byte at \emph{i} constexpr byte_t operator[](int i) const { assertd(not _const, "Attempted to Access Const-Qualified Memory as Non-Const"); - assertd(i >= 0 && (size_t)i < _size, "Array Out of Bounds"); + assertd(i >= 0 && size_t(i) < _size, "Array Out of Bounds"); return _carr[i]; } /// /// \brief Cast Function /// \tparam T type to cast to - /// \returns a pointer to the underlying buffer interpreted as an array of \f$T\f$ + /// \returns a pointer to the underlying buffer interpreted as an array of \emph{T} template constexpr T* cast() { void* temp = _arr; @@ -119,7 +119,7 @@ public: /// /// \brief Const Cast Function /// \tparam T type to cast to - /// \returns a pointer to the underlying buffer interpreted as an array of \f$T\f$ + /// \returns a pointer to the underlying buffer interpreted as an array of \emph{T} template constexpr const T* cast() const { const void* temp = _carr; @@ -166,8 +166,8 @@ struct hash { h *= m; } - const uint8_t* b = (const uint8_t*)x; - switch (n & 7) { + const uint8_t* b = reinterpret_cast(x); + switch (n & 0x7) { case 7: h ^= uint64_t(b[6]) << 48; __attribute__((fallthrough)); case 6: h ^= uint64_t(b[5]) << 40; __attribute__((fallthrough)); case 5: h ^= uint64_t(b[4]) << 32; __attribute__((fallthrough)); diff --git a/include/fennec/memory/common.h b/include/fennec/memory/common.h index e090cb9..2a53965 100644 --- a/include/fennec/memory/common.h +++ b/include/fennec/memory/common.h @@ -38,6 +38,8 @@ namespace fennec { +// addressof =========================================================================================================== + /// /// \brief Returns the address of an object regardless of whether the `&` operators is implemented. /// \tparam TypeT The type of the objects @@ -48,24 +50,45 @@ constexpr TypeT* addressof(TypeT& obj) { return FENNEC_BUILTIN_ADDRESSOF(obj); } + + +// memchr ============================================================================================================== + /// -/// \brief Finds the first occurence of ```static_cast(ch)``` in the first \f$n\f$ bytes +/// \brief Finds the first occurrence of `static_cast(ch)` in the first \emph{n} bytes /// \param arr Pointer to the object, interpreted as an array of bytes /// \param ch The byte to search for /// \param n The number of bytes to search -/// \returns A pointer to the location of \f$ch\f$, otherwise \f$nullptr\f$ if \f$ch\f$ is not found. -using ::memchr; -using ::wmemchr; +/// \returns A pointer to the location of \emph{ch}, otherwise \emph{nullptr} if \emph{ch} is not found. +constexpr const void* memchr(const void* arr, int ch, size_t n) { + return ::memchr(arr, ch, n); +} /// -/// \brief Compares the bytes of \f$lhs\f$ with \f$rhs\f$. +/// \brief Finds the first occurrence of `static_cast(ch)` in the first \emph{n} characters +/// \param arr Pointer to the object, interpreted as an array of \emph{wchar_t} +/// \param ch The byte to search for +/// \param n The number of characters to search +/// \returns A pointer to the location of \emph{ch}, otherwise \emph{nullptr} if \emph{ch} is not found. +constexpr const wchar_t* wmemchr(const wchar_t* arr, wchar_t ch, size_t n) { + return ::wmemchr(arr, ch, n); +} + + + +// memcmp ============================================================================================================== + +/// +/// \brief Compares the bytes of \emph{lhs} with \emph{rhs}. /// \param lhs The first object, interpreted as an array of bytes /// \param rhs The second object, interpreted as an array of bytes /// \param n The number of bytes to parse -/// \returns \f$0\f$ if the first \f$n\f$ bytes of \f$lhs\f$ and \f$rhs\f$ are equivalent. Otherwise, returns \f$1\f$ -/// for the first byte \f$b\f$ where \f$lhs[b] > \f$ rhs[b]\f$, and \f$-1\f$ for \f$ -using ::memcmp; -using ::wmemcmp; +/// \returns \math{0} if the first \emph{n} bytes of \emph{lhs} and \emph{rhs} are equivalent. Otherwise, returns a positive value +/// for the first byte \math{b} where \math{\textbf{lhs}[b] > \textbf{rhs}[b]}, and a negative value +/// for the first byte \math{b} where \math{\textbf{lhs}[b] < \textbf{rhs}[b]} +constexpr int memcmp(const void* lhs, const void* rhs, size_t n) { + return ::memcmp(lhs, rhs, n); +} /// /// \brief Safe version of memcmp @@ -73,26 +96,58 @@ using ::wmemcmp; /// \param rhs The second object, interpreted as an array of bytes /// \param n0 The size, in bytes, of lhs /// \param n1 The size, in bytes, of rhs -/// \returns \f$0\f$ if the first \f$min(n0, n1)\f$ bytes of \f$lhs\f$ and \f$rhs\f$ are equivalent. Otherwise, returns \f$1\f$ -/// for the first byte \f$b\f$ where \f$lhs[b] > \f$ rhs[b]\f$, and \f$-1\f$ for \f$ +/// \returns \math{0} if the first \emph{min(n0, n1)} bytes of \emph{lhs} and \emph{rhs} are equivalent. Otherwise, returns a positive value +/// for the first byte \math{b} where \math{\textbf{lhs}[b] > \textbf{rhs}[b]}, and a negative value +/// for the first byte \math{b} where \math{\textbf{lhs}[b] < \textbf{rhs}[b]} constexpr int memcmp_s(const void* lhs, size_t n0, const void* rhs, size_t n1) { - return memcmp(lhs, rhs, n0 < n1 ? n0 : n1); + return ::memcmp(lhs, rhs, n0 < n1 ? n0 : n1); +} + + +/// +/// \brief Compares the characters of \emph{lhs} with \emph{rhs}. +/// \param lhs The first object, interpreted as an array of \emph{wchar_t} +/// \param rhs The second object, interpreted as an array of \emph{wchar_t} +/// \param n The number of characters to parse +/// \returns \emph{0} if the first \emph{n} characters of \emph{lhs} and \emph{rhs} are equivalent. Otherwise, returns a positive value +/// for the first character \math{c} where \math{\textbf{lhs}[c] > \textbf{rhs}[c]}, and a negative value +/// for the first character \math{c} where \math{\textbf{lhs}[c] < \textbf{rhs}[c]} +constexpr int wmemcmp(const wchar_t* lhs, const wchar_t* rhs, size_t n) { + return ::wmemcmp(lhs, rhs, n); } /// -/// \brief Copies the first \f$n\f$ bytes of \f$src\f$ to \f$dst\f$. +/// \brief Safe version of memcmp +/// \param lhs The first object, interpreted as an array of \emph{wchar_t} +/// \param rhs The second object, interpreted as an array of \emph{wchar_t} +/// \param n0 The size, in characters, of lhs +/// \param n1 The size, in characters, of rhs +/// \returns \emph{0} if the first \emph{min(n0, n1)} character of \emph{lhs} and \emph{rhs} are equivalent. Otherwise, returns a positive value +/// for the first character \math{c} where \math{\textbf{lhs}[c] > \textbf{rhs}[c]}, and a negative value +/// for the first character \math{c} where \math{\textbf{lhs}[c] < \textbf{rhs}[c]} +constexpr int wmemcmp_s(const wchar_t* lhs, size_t n0, const wchar_t* rhs, size_t n1) { + return ::wmemcmp(lhs, rhs, n0 < n1 ? n0 : n1); +} + + + +// memcmp ============================================================================================================== + +/// +/// \brief Copies the first \emph{n} bytes of \emph{src} to \emph{dst}. /// \param dst The destination object, interpreted as an array of bytes /// \param src The source object, interpreted as an array of bytes /// \param n The number of bytes to copy -/// \returns \f$dst\f$ +/// \returns \emph{dst} /// -/// \details memcpy does not do any checking for whether \f$dst\f$ and \f$src\f$ overlap. Let \f$k\f$ be the number of -/// bytes of which \f$dst\f$ and \f$src\f$. If \f$k > 0 & src < dst\f$ then the first \f$k\f$ elements of -/// \f$src\f$ will be repeated in \f$dst\f$ with a period of \f$k\f$. +/// \details memcpy does not do any checking for whether \emph{dst} and \emph{src} overlap. Let \math{k} be the offset +/// by which \emph{dst} and \emph{src} overlap. If \math{k > 0 & \textbf{src} < \textbf{dst}} then the first \math{k} elements of +/// \emph{src} will be repeated in \emph{dst} with a period of \math{k}. /// /// A full mathematical proof of this function is possible in Set Theory. -using ::memcpy; -using ::wmemcpy; +constexpr void* memcpy(void* dst, const void* src, size_t n) { + return ::memcpy(dst, src, n); +} /// /// \brief Safe version of memcpy @@ -100,19 +155,64 @@ using ::wmemcpy; /// \param src The source object, interpreted as an array of bytes /// \param n0 The size, in bytes, of dst /// \param n1 The size, in bytes, of src -/// \returns \f$dst\f$ +/// \returns \emph{dst} +/// +/// \details memcpy does not do any checking for whether \emph{dst} and \emph{src} overlap. Let \math{k} be the offset +/// by which \emph{dst} and \emph{src} overlap. If \math{k > 0 & \textbf{src} < \textbf{dst}} then the first \math{k} elements of +/// \emph{src} will be repeated in \emph{dst} with a period of \math{k}. +/// +/// A full mathematical proof of this function is possible in Set Theory. constexpr void* memcpy_s(void* dst, size_t n0, const void* src, size_t n1) { - return memcpy(dst, src, n0 < n1 ? n0 : n1); + return ::memcpy(dst, src, n0 < n1 ? n0 : n1); +} + + +/// +/// \brief Copies the first \emph{n} characters of \emph{src} to \emph{dst}. +/// \param dst The destination object, interpreted as an array of \emph{wchar_t} +/// \param src The source object, interpreted as an array of \emph{wchar_t} +/// \param n The number of characters to copy +/// \returns \emph{dst} +/// +/// \details wmemcpy does not do any checking for whether \emph{dst} and \emph{src} overlap. Let \math{k} be the offset +/// by which \emph{dst} and \emph{src} overlap. If \math{k > 0 & \textbf{src} < \textbf{dst}} then the first \math{k} elements of +/// \emph{src} will be repeated in \emph{dst} with a period of \math{k}. +/// +/// A full mathematical proof of this function is possible in Set Theory. +constexpr void* wmemcpy(wchar_t* dst, const wchar_t* src, size_t n) { + return ::wmemcpy(dst, src, n); } /// -/// \brief Copies the first \f$n\f$ bytes of \f$src\f$ to \f$dst\f$, with overlap correction.. +/// \brief Safe version of wmemcpy +/// \param dst The destination object, interpreted as an array of \emph{wchar_t} +/// \param src The source object, interpreted as an array of \emph{wchar_t} +/// \param n0 The size, in characters, of dst +/// \param n1 The size, in characters, of src +/// \returns \emph{dst} +/// +/// \details wmemcpy does not do any checking for whether \emph{dst} and \emph{src} overlap. Let \math{k} be the offset +/// by which \emph{dst} and \emph{src} overlap. If \math{k > 0 & \textbf{src} < \textbf{dst}} then the first \math{k} elements of +/// \emph{src} will be repeated in \emph{dst} with a period of \math{k}. +/// +/// A full mathematical proof of this function is possible in Set Theory. +constexpr void* wmemcpy_s(wchar_t* dst, size_t n0, const wchar_t* src, size_t n1) { + return ::wmemcpy(dst, src, n0 < n1 ? n0 : n1); +} + + + +// memmove ============================================================================================================= + +/// +/// \brief Copies the first \emph{n} bytes of \emph{src} to \emph{dst}, with overlap correction. /// \param dst The destination object, interpreted as an array of bytes /// \param src The source object, interpreted as an array of bytes /// \param n The number of bytes to copy -/// \returns \f$dst\f$ -using ::memmove; -using ::wmemmove; +/// \returns \emph{dst} +constexpr void* memmove(void* dst, const void* src, size_t n) { + return ::memmove(dst, src, n); +} /// /// \brief Safe version of memmove @@ -120,19 +220,54 @@ using ::wmemmove; /// \param src The source object, interpreted as an array of bytes /// \param n0 The size, in bytes, of dst /// \param n1 The size, in bytes, of src -/// \returns \f$dst\f$ +/// \returns \emph{dst} constexpr void* memmove_s(void* dst, size_t n0, const void* src, size_t n1) { - return memmove(dst, src, n0 < n1 ? n0 : n1); + return ::memmove(dst, src, n0 < n1 ? n0 : n1); +} + + +/// +/// \brief Copies the first \emph{n} characters of \emph{src} to \emph{dst}, with overlap correction. +/// \param dst The destination object, interpreted as an array of \emph{wchar_t} +/// \param src The source object, interpreted as an array of \emph{wchar_t} +/// \param n The number of characters to copy +/// \returns \emph{dst} +constexpr void* wmemmove(wchar_t* dst, const wchar_t* src, size_t n) { + return ::wmemmove(dst, src, n); } /// -/// \brief Sets all bytes of \f$dst\f$ to \f$ch\f$, interpreted as an \f$uint8_t\f$ +/// \brief Safe version of wmemmove +/// \param dst The destination object, interpreted as an array of \emph{wchar_t} +/// \param src The source object, interpreted as an array of \emph{wchar_t} +/// \param n0 The size, in characters, of dst +/// \param n1 The size, in characters, of src +/// \returns \emph{dst} +constexpr wchar_t* wmemmove_s(wchar_t* dst, size_t n0, const wchar_t* src, size_t n1) { + return ::wmemmove(dst, src, n0 < n1 ? n0 : n1); +} + + + +// memset ============================================================================================================== + +/// +/// \brief Sets all bytes of \emph{dst} to \emph{ch}, interpreted as an \emph{uint8_t} /// \param dst The destination object, interpreted as an array of bytes -/// \param ch The value, interpreted as an \f$uint8\_t\f$ +/// \param ch The value, interpreted as an \emph{uint8_t} /// \param n The number of bytes to set -/// \returns \f$dst\f$ -using ::memset; -using ::wmemset; +constexpr void memset(void* dst, int ch, size_t n) { + ::memset(dst, ch, n); +} + +/// +/// \brief Sets all characters of \emph{dst} to \emph{ch} +/// \param dst The destination object, interpreted as an array of \emph{wchar_t} +/// \param ch The value, interpreted as an \emph{uint8_t} +/// \param n The number of characters to set +constexpr void wmemset(wchar_t* dst, wchar_t ch, size_t n) { + ::wmemset(dst, ch, n); +} } diff --git a/include/fennec/memory/detail/_string.h b/include/fennec/memory/detail/_string.h index dc7fab1..cfd5278 100644 --- a/include/fennec/memory/detail/_string.h +++ b/include/fennec/memory/detail/_string.h @@ -23,7 +23,7 @@ // see https://git.mslockbo.org/mslockbo/fennec/src/commit/0eeb7ae3cff9d78e98dc5d9fc09bcb98b10986b9 for previous // implementation -#if FENNEC_COMPILER_GCC +#if FENNEC_GLIBC #ifndef __OPTIMIZE__ # define __OPTIMIZE__ #else @@ -34,7 +34,7 @@ #include #include -#if FENNEC_COMPILER_GCC +#if FENNEC_GLIBC #ifndef FENNEC_OPTIMIZE_FOUND #undef __OPTIMIZE__ #endif diff --git a/include/fennec/memory/new.h b/include/fennec/memory/new.h index bd5e86a..cfc76fb 100644 --- a/include/fennec/memory/new.h +++ b/include/fennec/memory/new.h @@ -54,7 +54,7 @@ struct nothrow_t size_t pagesize(); /// -/// \brief Default construct the object of type \f$TypeT\f$ at \f$ptr\f$ +/// \brief Default construct the object of type \emph{TypeT} at \emph{ptr} /// \tparam TypeT the type to construct /// \param ptr the pointer to the object to construct template void construct(TypeT* ptr) { @@ -62,7 +62,7 @@ template void construct(TypeT* ptr) { } /// -/// \brief Copy construct the object of type \f$TypeT\f$ at \f$ptr\f$ +/// \brief Copy construct the object of type \emph{TypeT} at \emph{ptr} /// \tparam TypeT the type to construct /// \param ptr the pointer to the object to construct /// \param val the value to copy @@ -71,7 +71,7 @@ template void construct(TypeT* ptr, const TypeT& val) { } /// -/// \brief Move construct the object of type \f$TypeT\f$ at \f$ptr\f$ +/// \brief Move construct the object of type \emph{TypeT} at \emph{ptr} /// \tparam TypeT the type to construct /// \param ptr the pointer to the object to construct /// \param val the value to take ownership of @@ -80,7 +80,7 @@ template void construct(TypeT* ptr, TypeT&& val) { } /// -/// \brief Variadic construct the object of type \f$TypeT\f$ at \f$ptr\f$ +/// \brief Variadic construct the object of type \emph{TypeT} at \emph{ptr} /// \tparam TypeT the type to construct /// \tparam ArgsT the argument types /// \param ptr the pointer to the object to construct @@ -90,7 +90,7 @@ template void construct(TypeT* ptr, ArgsT&&... } /// -/// \brief Destruct the object of type \f$TypeT\f$ at \f$ptr\f$ +/// \brief Destruct the object of type \emph{TypeT} at \emph{ptr} /// \tparam TypeT the type to destruct /// \param ptr the pointer to the object to destruct template void destruct(TypeT* ptr) { diff --git a/include/fennec/memory/pointers.h b/include/fennec/memory/pointers.h index 896bf30..69e7763 100644 --- a/include/fennec/memory/pointers.h +++ b/include/fennec/memory/pointers.h @@ -26,7 +26,7 @@ namespace fennec { /// -/// \brief Struct for wrapping C++ \f$delete\f$ +/// \brief Struct for wrapping C++ \emph{delete} /// \tparam TypeT The type of the buffer to be deleted template struct default_delete @@ -42,7 +42,7 @@ struct default_delete constexpr default_delete(const default_delete&) noexcept {} /// - /// \brief Function Call Operator, calls \f$delete\f$ on \f$ptr\f$ + /// \brief Function Call Operator, calls \emph{delete} on \emph{ptr} /// \param ptr Memory resource to delete constexpr void operator()(TypeT* ptr) const noexcept { static_assert(not is_void_v, "cannot delete a pointer to an incomplete type"); @@ -67,7 +67,7 @@ struct default_delete constexpr default_delete(const default_delete&) noexcept {} /// - /// \brief Function Call Operator, calls \f$delete\f$ on \f$ptr\f$ + /// \brief Function Call Operator, calls \emph{delete} on \emph{ptr} /// \param ptr Memory resource to delete template requires requires { is_convertible_v == true; } constexpr void operator()(TypeT* ptr) const noexcept { @@ -122,7 +122,7 @@ public: constexpr unique_ptr(nullptr_t) noexcept : unique_ptr(nullptr, delete_t()) {} /// - /// \brief Pointer Constructor, creates a unique_ptr that owns \f$ptr\f$ with deleter \f$del\f$ + /// \brief Pointer Constructor, creates a unique_ptr that owns \emph{ptr} with deleter \emph{del} /// \param ptr The resource to own /// \param del The deleter explicit constexpr unique_ptr(pointer_t ptr, const delete_t& del = delete_t()) @@ -138,14 +138,16 @@ public: } /// - /// \brief Move Constructor, transfers ownership from \f$other\f$ + /// \brief Move Constructor, transfers ownership from \emph{other} /// \param other The unique_ptr to take ownership from template requires(is_base_of_v) constexpr unique_ptr(unique_ptr&& other) : _handle(other.release()) { } - // Delete copy constructor + /// + /// \brief Copy Constructor + /// \details Deleted constexpr unique_ptr(const unique_ptr&) = delete; /// @@ -166,18 +168,21 @@ public: /// /// \brief move constructor /// \param r the pointer to take ownership of - /// \returns a reference to self + /// \returns a reference to \emph{this} constexpr unique_ptr& operator=(unique_ptr&& r) noexcept { _delete = r._delete; fennec::swap(_handle, r._handle); return *this; } - /// @} - -private: + /// + /// \brief Copy Assignment + /// \details Deleted + /// \returns Deleted constexpr unique_ptr& operator=(const unique_ptr&) = delete; + /// @} + // Properties ========================================================================================================== public: @@ -186,14 +191,14 @@ public: /// @{ /// - /// \returns \f$true\f$ if there is not a held pointer, \f$false\f$ otherwise + /// \returns \emph{true} if there is not a held pointer, \emph{false} otherwise bool is_empty() { return _handle == nullptr; } /// /// \brief implicit boolean conversion - /// \returns \f$true\f$ if there is a held pointer, \f$false\f$ otherwise + /// \returns \emph{true} if there is a held pointer, \emph{false} otherwise operator bool() const { return _handle != nullptr; } @@ -278,11 +283,11 @@ private: }; /// -/// \brief Creates a unique pointer holding an object of type \f$TypeT\f$ +/// \brief Creates a unique pointer holding an object of type \emph{TypeT} /// \tparam TypeT The type /// \tparam ArgsT The constructor arguments, automatically deduced /// \param args The constructor arguments -/// \returns A unique pointer holding a heap allocated object of type \f$TypeT\f$ constructed with arguments \f$args\f$ +/// \returns A unique pointer holding a heap allocated object of type \emph{TypeT} constructed with arguments \emph{args} template unique_ptr make_unique(ArgsT&&...args) { return unique_ptr(new TypeT(fennec::forward(args)...)); diff --git a/include/fennec/platform/interface/display_server.h b/include/fennec/platform/interface/display_server.h index e4a1402..8add18e 100644 --- a/include/fennec/platform/interface/display_server.h +++ b/include/fennec/platform/interface/display_server.h @@ -51,9 +51,9 @@ class display_server; /// /// \details An implementation for a display server should inherit `display_server_base` and note the following: /// -/// For a server type \f$DisplayT\f$; any \f$gfxcontext\f$ implementation that wishes to implement \f$DisplayT\f$ -/// must provide a constructor that accepts a `DisplayT*`. `DisplayT::ctx_registry::register_type` must then be -/// called for the \f$gfxcontext\f$ implementation. +/// For a server type \emph{DisplayT}; any `gfxcontext` implementation that wishes to implement \emph{DisplayT} +/// must provide a constructor that accepts a \emph{DisplayT*}. `DisplayT::ctx_registry::register_type()` must then be +/// called for the `gfxcontext` implementation. class display_server : public type_registry { // Definitions & Constants ============================================================================================= public: @@ -136,13 +136,13 @@ public: /// /// \brief feature support checking function /// \param feature the feature to check - /// \returns \f$true\f$ if the feature is supported, \f$false\f$ otherwise + /// \returns \emph{true} if the feature is supported, \emph{false} otherwise bool has_feature(uint32_t feature) const { return features.test(feature); } /// - /// \returns \f$true\f$ if connected to the display server, \f$false\f$ otherwise + /// \returns \emph{true} if connected to the display server, \emph{false} otherwise virtual bool connected() const = 0; /// @} diff --git a/include/fennec/platform/interface/platform.h b/include/fennec/platform/interface/platform.h index 1abacd5..ad61970 100644 --- a/include/fennec/platform/interface/platform.h +++ b/include/fennec/platform/interface/platform.h @@ -87,14 +87,16 @@ public: /// \brief constructor platform(); + /// + /// \brief Copy Constructor + /// \details Deleted, no semantics for copying a platform + platform(const platform&) = delete; + /// /// \brief destructor virtual ~platform() = default; -private: - platform(const platform&) = delete; - /// @} diff --git a/include/fennec/platform/interface/window.h b/include/fennec/platform/interface/window.h index 794b0d2..1193db6 100644 --- a/include/fennec/platform/interface/window.h +++ b/include/fennec/platform/interface/window.h @@ -164,15 +164,21 @@ public: /// /// \returns the current configuration of the window - const config& get_config() const { return cfg; } + const config& get_config() const { + return cfg; + } /// /// \returns the parent window - window* get_parent() const { return parent; } + window* get_parent() const { + return parent; + } /// /// \returns the nearest top-level window in the hierarchy - window* get_root() const { return root; } + window* get_root() const { + return root; + } /// /// \returns the underlying handle of the window @@ -208,19 +214,29 @@ public: /// /// \returns the width of the window - int get_width() const { return state.rect.size.x; } + int get_width() const { + return state.rect.size.x; + } /// /// \returns the height of the window - int get_height() const { return state.rect.size.y; } + int get_height() const { + return state.rect.size.y; + } /// /// \returns the x position of the window - int get_pos_x() const { return state.rect.position.x; } + int get_pos_x() const { + return state.rect.position.x; + } /// /// \returns the y position of the window - int get_pos_y() const { return state.rect.position.y; } + int get_pos_y() const { + return state.rect.position.y; + } + + virtual void set_size(const ivec2& size) = 0; /// @} @@ -234,22 +250,22 @@ public: /// /// \brief tests if the window is visible - /// \returns \f$true\f$ if the window is visible, \f$false\f$ otherwise + /// \returns \emph{true} if the window is visible, \emph{false} otherwise bool is_visible() const { return state.flags.test(state_visible); } /// /// \brief tests if the window is a child - /// \returns \f$true\f$ if the window is a child, \f$false\f$ otherwise + /// \returns \emph{true} if the window is a child, \emph{false} otherwise bool is_child() const { return state.flags.test(state_child); } /// /// \brief tests if the window is running - /// \returns \f$true\f$ if the window is running, \f$false\f$ otherwise + /// \returns \emph{true} if the window is running, \emph{false} otherwise bool is_running() const { return state.flags.test(state_running); } /// /// \brief tests if the window is suspended - /// \returns \f$true\f$ if the window is suspended, \f$false\f$ otherwise + /// \returns \emph{true} if the window is suspended, \emph{false} otherwise bool is_suspended() const { return state.flags.test(state_suspended); } /// @} @@ -265,48 +281,48 @@ public: /// /// \brief tests a specific flag /// \param flag the flag from `window::flag_` - /// \returns \f$true\f$ if the flag is set, \f$false\f$ otherwise + /// \returns \emph{true} if the flag is set, \emph{false} otherwise bool get_flag(uint8_t flag) const { return cfg.flags.test(flag); } /// /// \brief check if the window is flagged to always be on top of other windows - /// \returns \f$true\f$ if set, \f$false\f$ otherwise + /// \returns \emph{true} if set, \emph{false} otherwise bool is_always_on_top() const { return get_flag(flag_always_on_top); } /// /// \brief check if the window is flagged to have no window decorations - /// \returns \f$true\f$ if set, \f$false\f$ otherwise + /// \returns \emph{true} if set, \emph{false} otherwise bool is_borderless() const { return get_flag(flag_borderless); } /// /// \brief check if the window is flagged to be modal - /// \returns \f$true\f$ if set, \f$false\f$ otherwise + /// \returns \emph{true} if set, \emph{false} otherwise bool is_modal() const { return get_flag(flag_modal); } /// /// \brief check if the window is flagged to pass mouse input to windows underneath from the same application - /// \returns \f$true\f$ if set, \f$false\f$ otherwise + /// \returns \emph{true} if set, \emph{false} otherwise bool is_passing_mouse() const { return get_flag(flag_pass_mouse); } /// /// \brief check if the window is flagged as a popup - /// \returns \f$true\f$ if set, \f$false\f$ otherwise + /// \returns \emph{true} if set, \emph{false} otherwise bool is_popup() const { return get_flag(flag_popup); } /// /// \brief check if the window is flagged to be resizable - /// \returns \f$true\f$ if set, \f$false\f$ otherwise + /// \returns \emph{true} if set, \emph{false} otherwise bool is_resizable() const { return get_flag(flag_resizable); } /// /// \brief check if the window is flagged to be transparent - /// \returns \f$true\f$ if set, \f$false\f$ otherwise + /// \returns \emph{true} if set, \emph{false} otherwise bool is_transparent() const { return get_flag(flag_transparent); } /// /// \brief check if the window is flagged to be unfocusable - /// \returns \f$true\f$ if set, \f$false\f$ otherwise + /// \returns \emph{true} if set, \emph{false} otherwise bool is_no_focus() const { return get_flag(flag_no_focus); } @@ -314,55 +330,55 @@ public: /// \brief sets a specific flag /// \param flag the flag from `window::flag_` /// \param val the value to set the flag to - /// \returns \f$true\f$ on success, \f$false\f$ otherwise + /// \returns \emph{true} on success, \emph{false} otherwise virtual bool set_flag(uint8_t flag, bool val) = 0; /// /// \brief sets whether to always be on top of other windows /// \param val the value to set the flag to - /// \returns \f$true\f$ on success, \f$false\f$ otherwise + /// \returns \emph{true} on success, \emph{false} otherwise bool set_always_on_top(bool val) { return set_flag(flag_always_on_top, val); } /// /// \brief sets whether to have no window decorations /// \param val the value to set the flag to - /// \returns \f$true\f$ on success, \f$false\f$ otherwise + /// \returns \emph{true} on success, \emph{false} otherwise bool set_borderless(bool val) { return set_flag(flag_borderless, val); } /// /// \brief sets whether to be modal /// \param val the value to set the flag to - /// \returns \f$true\f$ on success, \f$false\f$ otherwise + /// \returns \emph{true} on success, \emph{false} otherwise bool set_modal(bool val) { return set_flag(flag_modal, val); } /// /// \brief sets whether to pass mouse input to windows underneath from the same application /// \param val the value to set the flag to - /// \returns \f$true\f$ on success, \f$false\f$ otherwise + /// \returns \emph{true} on success, \emph{false} otherwise bool set_passing_mouse(bool val) { return set_flag(flag_pass_mouse, val); } /// /// \brief sets whether the window is a popup /// \param val the value to set the flag to - /// \returns \f$true\f$ on success, \f$false\f$ otherwise + /// \returns \emph{true} on success, \emph{false} otherwise bool set_popup(bool val) { return set_flag(flag_popup, val); } /// /// \brief sets whether to be resizable /// \param val the value to set the flag to - /// \returns \f$true\f$ on success, \f$false\f$ otherwise + /// \returns \emph{true} on success, \emph{false} otherwise bool set_resizable(bool val) { return set_flag(flag_resizable, val); } /// /// \brief sets whetherto be transparent /// \param val the value to set the flag to - /// \returns \f$true\f$ on success, \f$false\f$ otherwise + /// \returns \emph{true} on success, \emph{false} otherwise bool set_transparent(bool val) { return set_flag(flag_transparent, val); } /// /// \brief sets whether to be unfocusable /// \param val the value to set the flag to - /// \returns \f$true\f$ on success, \f$false\f$ otherwise + /// \returns \emph{true} on success, \emph{false} otherwise bool set_no_focus(bool val) { return set_flag(flag_no_focus, val); } /// @} @@ -385,10 +401,12 @@ public: // Protected Member Variables ========================================================================================== +public: + display_server* const server; //!< the display server the window belongs to + window* const parent; //!< the parent window + window* const root; //!< the nearest top-level window in the hierarchy + protected: - display_server* const server; //!< the display server the window belongs to - window* const parent; //!< the parent window - window* root; //!< the nearest top-level window in the hierarchy config cfg; //!< the current configuration state state; //!< the current state unique_ptr gfx_surface; //!< the corresponding graphics surface diff --git a/include/fennec/platform/linux/platform.h b/include/fennec/platform/linux/platform.h index 20a1596..7a52308 100644 --- a/include/fennec/platform/linux/platform.h +++ b/include/fennec/platform/linux/platform.h @@ -23,6 +23,8 @@ namespace fennec { +/// +/// \brief Platform Implementation for Linux-Based Operating Systems class linux_platform : public unix_platform { // Constructors & Destructor =========================================================================================== @@ -31,7 +33,7 @@ public: /// \name Constructors & Destructor ================================================================================ /// @{ - /// \brief constructor + /// \brief Linux Platform Constructor linux_platform() : unix_platform() { } @@ -39,11 +41,18 @@ public: /// @} -// +// Initialization ====================================================================================================== + + /// \name Initialization + /// @{ void initialize() override; //!< platform initialization void shutdown() override; //!< platform shutdown + /// @} + + +private: FENNEC_RTTI_CLASS_ENABLE(unix_platform) { } }; diff --git a/include/fennec/platform/linux/wayland/lib/headers/wayland-client-protocols.h b/include/fennec/platform/linux/wayland/lib/headers/wayland-client-protocols.h index 82626f4..3ddfef4 100644 --- a/include/fennec/platform/linux/wayland/lib/headers/wayland-client-protocols.h +++ b/include/fennec/platform/linux/wayland/lib/headers/wayland-client-protocols.h @@ -1,4 +1,4 @@ -/* Generated by wayland-scanner 1.24.0 */ +/* Generated by wayland-scanner 1.25.0 */ #ifndef WAYLAND_CLIENT_PROTOCOL_H #define WAYLAND_CLIENT_PROTOCOL_H @@ -841,23 +841,9 @@ extern const struct wl_interface wl_subcompositor_interface; * hidden, or if a NULL wl_buffer is applied. These rules apply * recursively through the tree of surfaces. * - * The behaviour of a wl_surface.commit request on a sub-surface - * depends on the sub-surface's mode. The possible modes are - * synchronized and desynchronized, see methods - * wl_subsurface.set_sync and wl_subsurface.set_desync. Synchronized - * mode caches the wl_surface state to be applied when the parent's - * state gets applied, and desynchronized mode applies the pending - * wl_surface state directly. A sub-surface is initially in the - * synchronized mode. - * - * Sub-surfaces also have another kind of state, which is managed by - * wl_subsurface requests, as opposed to wl_surface requests. This - * state includes the sub-surface position relative to the parent - * surface (wl_subsurface.set_position), and the stacking order of - * the parent and its sub-surfaces (wl_subsurface.place_above and - * .place_below). This state is applied when the parent surface's - * wl_surface state is applied, regardless of the sub-surface's mode. - * As the exception, set_sync and set_desync are effective immediately. + * A sub-surface can be in one of two modes. The possible modes are + * synchronized and desynchronized, see methods wl_subsurface.set_sync and + * wl_subsurface.set_desync. * * The main surface can be thought to be always in desynchronized mode, * since it does not have a parent in the sub-surfaces sense. @@ -869,6 +855,15 @@ extern const struct wl_interface wl_subcompositor_interface; * synchronized mode, and then assume that all its child and grand-child * sub-surfaces are synchronized, too, without explicitly setting them. * + * If a surface behaves as in synchronized mode, it is effectively + * synchronized, otherwise it is effectively desynchronized. + * + * A sub-surface is initially in the synchronized mode. + * + * The wl_subsurface interface has requests which modify double-buffered + * state of the parent surface (wl_subsurface.set_position, .place_above and + * .place_below). + * * Destroying a sub-surface takes effect immediately. If you need to * synchronize the removal of a sub-surface to the parent surface update, * unmap the sub-surface first by attaching a NULL wl_buffer, update parent, @@ -899,23 +894,9 @@ extern const struct wl_interface wl_subcompositor_interface; * hidden, or if a NULL wl_buffer is applied. These rules apply * recursively through the tree of surfaces. * - * The behaviour of a wl_surface.commit request on a sub-surface - * depends on the sub-surface's mode. The possible modes are - * synchronized and desynchronized, see methods - * wl_subsurface.set_sync and wl_subsurface.set_desync. Synchronized - * mode caches the wl_surface state to be applied when the parent's - * state gets applied, and desynchronized mode applies the pending - * wl_surface state directly. A sub-surface is initially in the - * synchronized mode. - * - * Sub-surfaces also have another kind of state, which is managed by - * wl_subsurface requests, as opposed to wl_surface requests. This - * state includes the sub-surface position relative to the parent - * surface (wl_subsurface.set_position), and the stacking order of - * the parent and its sub-surfaces (wl_subsurface.place_above and - * .place_below). This state is applied when the parent surface's - * wl_surface state is applied, regardless of the sub-surface's mode. - * As the exception, set_sync and set_desync are effective immediately. + * A sub-surface can be in one of two modes. The possible modes are + * synchronized and desynchronized, see methods wl_subsurface.set_sync and + * wl_subsurface.set_desync. * * The main surface can be thought to be always in desynchronized mode, * since it does not have a parent in the sub-surfaces sense. @@ -927,6 +908,15 @@ extern const struct wl_interface wl_subcompositor_interface; * synchronized mode, and then assume that all its child and grand-child * sub-surfaces are synchronized, too, without explicitly setting them. * + * If a surface behaves as in synchronized mode, it is effectively + * synchronized, otherwise it is effectively desynchronized. + * + * A sub-surface is initially in the synchronized mode. + * + * The wl_subsurface interface has requests which modify double-buffered + * state of the parent surface (wl_subsurface.set_position, .place_above and + * .place_below). + * * Destroying a sub-surface takes effect immediately. If you need to * synchronize the removal of a sub-surface to the parent surface update, * unmap the sub-surface first by attaching a NULL wl_buffer, update parent, @@ -1307,6 +1297,7 @@ wl_callback_destroy(struct wl_callback *wl_callback) #define WL_COMPOSITOR_CREATE_SURFACE 0 #define WL_COMPOSITOR_CREATE_REGION 1 +#define WL_COMPOSITOR_RELEASE 2 /** @@ -1317,6 +1308,10 @@ wl_callback_destroy(struct wl_callback *wl_callback) * @ingroup iface_wl_compositor */ #define WL_COMPOSITOR_CREATE_REGION_SINCE_VERSION 1 +/** + * @ingroup iface_wl_compositor + */ +#define WL_COMPOSITOR_RELEASE_SINCE_VERSION 7 /** @ingroup iface_wl_compositor */ static inline void @@ -1377,6 +1372,18 @@ wl_compositor_create_region(struct wl_compositor *wl_compositor) return (struct wl_region *) id; } +/** + * @ingroup iface_wl_compositor + * + * This request destroys the wl_compositor. This has no effect on any other objects. + */ +static inline void +wl_compositor_release(struct wl_compositor *wl_compositor) +{ + wl_proxy_marshal_flags((struct wl_proxy *) wl_compositor, + WL_COMPOSITOR_RELEASE, NULL, wl_proxy_get_version((struct wl_proxy *) wl_compositor), WL_MARSHAL_FLAG_DESTROY); +} + #define WL_SHM_POOL_CREATE_BUFFER 0 #define WL_SHM_POOL_DESTROY 1 #define WL_SHM_POOL_RESIZE 2 @@ -1516,7 +1523,8 @@ enum wl_shm_error { * * The drm format codes match the macros defined in drm_fourcc.h, except * argb8888 and xrgb8888. The formats actually supported by the compositor - * will be reported by the format event. + * will be reported by the format event. See drm_fourcc.h for more detailed + * format descriptions. * * For all wl_shm formats and unless specified in another protocol * extension, pre-multiplied alpha is used for pixel values. @@ -1978,6 +1986,86 @@ enum wl_shm_format { * 2x2 subsampled Cr:Cb plane 10 bits per channel packed */ WL_SHM_FORMAT_P030 = 0x30333050, + /** + * [47:0] R:G:B 16:16:16 little endian + */ + WL_SHM_FORMAT_RGB161616 = 0x38344752, + /** + * [47:0] B:G:R 16:16:16 little endian + */ + WL_SHM_FORMAT_BGR161616 = 0x38344742, + /** + * [15:0] R 16 little endian + */ + WL_SHM_FORMAT_R16F = 0x48202052, + /** + * [31:0] G:R 16:16 little endian + */ + WL_SHM_FORMAT_GR1616F = 0x48205247, + /** + * [47:0] B:G:R 16:16:16 little endian + */ + WL_SHM_FORMAT_BGR161616F = 0x48524742, + /** + * [31:0] R 32 little endian + */ + WL_SHM_FORMAT_R32F = 0x46202052, + /** + * [63:0] R:G 32:32 little endian + */ + WL_SHM_FORMAT_GR3232F = 0x46205247, + /** + * [95:0] R:G:B 32:32:32 little endian + */ + WL_SHM_FORMAT_BGR323232F = 0x46524742, + /** + * [127:0] R:G:B:A 32:32:32:32 little endian + */ + WL_SHM_FORMAT_ABGR32323232F = 0x46384241, + /** + * 2x1 subsampled Cr:Cb plane + */ + WL_SHM_FORMAT_NV20 = 0x3032564e, + /** + * non-subsampled Cr:Cb plane + */ + WL_SHM_FORMAT_NV30 = 0x3033564e, + /** + * 2x2 subsampled Cb (1) and Cr (2) planes 10 bits per channel + */ + WL_SHM_FORMAT_S010 = 0x30313053, + /** + * 2x1 subsampled Cb (1) and Cr (2) planes 10 bits per channel + */ + WL_SHM_FORMAT_S210 = 0x30313253, + /** + * non-subsampled Cb (1) and Cr (2) planes 10 bits per channel + */ + WL_SHM_FORMAT_S410 = 0x30313453, + /** + * 2x2 subsampled Cb (1) and Cr (2) planes 12 bits per channel + */ + WL_SHM_FORMAT_S012 = 0x32313053, + /** + * 2x1 subsampled Cb (1) and Cr (2) planes 12 bits per channel + */ + WL_SHM_FORMAT_S212 = 0x32313253, + /** + * non-subsampled Cb (1) and Cr (2) planes 12 bits per channel + */ + WL_SHM_FORMAT_S412 = 0x32313453, + /** + * 2x2 subsampled Cb (1) and Cr (2) planes 16 bits per channel + */ + WL_SHM_FORMAT_S016 = 0x36313053, + /** + * 2x1 subsampled Cb (1) and Cr (2) planes 16 bits per channel + */ + WL_SHM_FORMAT_S216 = 0x36313253, + /** + * non-subsampled Cb (1) and Cr (2) planes 16 bits per channel + */ + WL_SHM_FORMAT_S416 = 0x36313453, }; #endif /* WL_SHM_FORMAT_ENUM */ @@ -1991,6 +2079,11 @@ struct wl_shm_listener { * * Informs the client about a valid pixel format that can be used * for buffers. Known formats include argb8888 and xrgb8888. + * + * Extensions to drm_fourcc.h (or the format enum) do not require + * increasing the wl_shm version; as a result, clients may receive + * format codes which were not in the list at the time the client + * was made. * @param format buffer pixel format */ void (*format)(void *data, @@ -3056,6 +3149,7 @@ enum wl_data_device_manager_dnd_action { #define WL_DATA_DEVICE_MANAGER_CREATE_DATA_SOURCE 0 #define WL_DATA_DEVICE_MANAGER_GET_DATA_DEVICE 1 +#define WL_DATA_DEVICE_MANAGER_RELEASE 2 /** @@ -3066,6 +3160,10 @@ enum wl_data_device_manager_dnd_action { * @ingroup iface_wl_data_device_manager */ #define WL_DATA_DEVICE_MANAGER_GET_DATA_DEVICE_SINCE_VERSION 1 +/** + * @ingroup iface_wl_data_device_manager + */ +#define WL_DATA_DEVICE_MANAGER_RELEASE_SINCE_VERSION 4 /** @ingroup iface_wl_data_device_manager */ static inline void @@ -3126,6 +3224,19 @@ wl_data_device_manager_get_data_device(struct wl_data_device_manager *wl_data_de return (struct wl_data_device *) id; } +/** + * @ingroup iface_wl_data_device_manager + * + * This request destroys the wl_data_device_manager. This has no effect on any other + * objects. + */ +static inline void +wl_data_device_manager_release(struct wl_data_device_manager *wl_data_device_manager) +{ + wl_proxy_marshal_flags((struct wl_proxy *) wl_data_device_manager, + WL_DATA_DEVICE_MANAGER_RELEASE, NULL, wl_proxy_get_version((struct wl_proxy *) wl_data_device_manager), WL_MARSHAL_FLAG_DESTROY); +} + #ifndef WL_SHELL_ERROR_ENUM #define WL_SHELL_ERROR_ENUM enum wl_shell_error { @@ -3691,6 +3802,10 @@ enum wl_surface_error { * surface was destroyed before its role object */ WL_SURFACE_ERROR_DEFUNCT_ROLE_OBJECT = 4, + /** + * no buffer was attached + */ + WL_SURFACE_ERROR_NO_BUFFER = 5, }; #endif /* WL_SURFACE_ERROR_ENUM */ @@ -3795,6 +3910,7 @@ wl_surface_add_listener(struct wl_surface *wl_surface, #define WL_SURFACE_SET_BUFFER_SCALE 8 #define WL_SURFACE_DAMAGE_BUFFER 9 #define WL_SURFACE_OFFSET 10 +#define WL_SURFACE_GET_RELEASE 11 /** * @ingroup iface_wl_surface @@ -3857,6 +3973,10 @@ wl_surface_add_listener(struct wl_surface *wl_surface, * @ingroup iface_wl_surface */ #define WL_SURFACE_OFFSET_SINCE_VERSION 5 +/** + * @ingroup iface_wl_surface + */ +#define WL_SURFACE_GET_RELEASE_SINCE_VERSION 7 /** @ingroup iface_wl_surface */ static inline void @@ -3937,9 +4057,11 @@ wl_surface_destroy(struct wl_surface *wl_surface) * If a pending wl_buffer has been committed to more than one wl_surface, * the delivery of wl_buffer.release events becomes undefined. A well * behaved client should not rely on wl_buffer.release events in this - * case. Alternatively, a client could create multiple wl_buffer objects - * from the same backing storage or use a protocol extension providing - * per-commit release notifications. + * case. Instead, clients hitting this case should use + * wl_surface.get_release or use a protocol extension providing per-commit + * release notifications (if none of these options are available, a + * fallback can be implemented by creating multiple wl_buffer objects from + * the same backing storage). * * Destroying the wl_buffer after wl_buffer.release does not change * the surface contents. Destroying the wl_buffer before wl_buffer.release @@ -4120,21 +4242,48 @@ wl_surface_set_input_region(struct wl_surface *wl_surface, struct wl_region *reg * etc.) is double-buffered. Protocol requests modify the pending state, * as opposed to the active state in use by the compositor. * - * A commit request atomically creates a content update from the pending - * state, even if the pending state has not been touched. The content - * update is placed in a queue until it becomes active. After commit, the - * new pending state is as documented for each related request. - * - * When the content update is applied, the wl_buffer is applied before all - * other state. This means that all coordinates in double-buffered state - * are relative to the newly attached wl_buffers, except for - * wl_surface.attach itself. If there is no newly attached wl_buffer, the - * coordinates are relative to the previous content update. - * * All requests that need a commit to become effective are documented * to affect double-buffered state. * * Other interfaces may add further double-buffered surface state. + * + * A commit request atomically creates a Content Update (CU) from the + * pending state, even if the pending state has not been touched. The + * content update is placed at the end of a per-surface queue until it + * becomes active. After commit, the new pending state is as documented for + * each related request. + * + * A CU is either a Desync Content Update (DCU) or a Sync Content Update + * (SCU). If the surface is effectively synchronized at the commit request, + * it is a SCU, otherwise a DCU. + * + * When a surface transitions from effectively synchronized to effectively + * desynchronized, all SCUs in its queue which are not reachable by any + * DCU become DCUs and dependency edges from outside the queue to these CUs + * are removed. + * + * See wl_subsurface for the definition of 'effectively synchronized' and + * 'effectively desynchronized'. + * + * When a CU is placed in the queue, the CU has a dependency on the CU in + * front of it and to the SCU at end of the queue of every direct child + * surface if that SCU exists and does not have another dependent. This can + * form a directed acyclic graph of CUs with dependencies as edges. + * + * In addition to surface state, the CU can have constraints that must be + * satisfied before it can be applied. Other interfaces may add CU + * constraints. + * + * All DCUs which do not have a SCU in front of themselves in their queue, + * are candidates. If the graph that's reachable by a candidate does not + * have any unsatisfied constraints, the entire graph must be applied + * atomically. + * + * When a CU is applied, the wl_buffer is applied before all other state. + * This means that all coordinates in double-buffered state are relative to + * the newly attached wl_buffers, except for wl_surface.attach itself. If + * there is no newly attached wl_buffer, the coordinates are relative to + * the previous content update. */ static inline void wl_surface_commit(struct wl_surface *wl_surface) @@ -4288,6 +4437,39 @@ wl_surface_offset(struct wl_surface *wl_surface, int32_t x, int32_t y) WL_SURFACE_OFFSET, NULL, wl_proxy_get_version((struct wl_proxy *) wl_surface), 0, x, y); } +/** + * @ingroup iface_wl_surface + * + * Create a callback for the release of the buffer attached by the client + * with wl_surface.attach. + * + * The compositor will release the buffer when it has finished its usage of + * the underlying storage for the relevant commit. Once the client receives + * this event, and assuming the associated buffer is not pending release + * from other wl_surface.commit requests, the client can safely re-use the + * buffer. + * + * Release callbacks are double-buffered state, and will be associated + * with the pending buffer at wl_surface.commit time. + * + * The callback_data passed in the wl_callback.done event is unused and + * is always zero. + * + * Sending this request without attaching a non-null buffer in the same + * content update is a protocol error. The compositor will send the + * no_buffer error in this case. + */ +static inline struct wl_callback * +wl_surface_get_release(struct wl_surface *wl_surface) +{ + struct wl_proxy *callback; + + callback = wl_proxy_marshal_flags((struct wl_proxy *) wl_surface, + WL_SURFACE_GET_RELEASE, &wl_callback_interface, wl_proxy_get_version((struct wl_proxy *) wl_surface), 0, NULL); + + return (struct wl_callback *) callback; +} + #ifndef WL_SEAT_CAPABILITY_ENUM #define WL_SEAT_CAPABILITY_ENUM /** @@ -6344,20 +6526,18 @@ wl_subsurface_destroy(struct wl_subsurface *wl_subsurface) /** * @ingroup iface_wl_subsurface * - * This schedules a sub-surface position change. + * This sets the position of the sub-surface, relative to the parent + * surface. + * * The sub-surface will be moved so that its origin (top left * corner pixel) will be at the location x, y of the parent surface * coordinate system. The coordinates are not restricted to the parent * surface area. Negative values are allowed. * - * The scheduled coordinates will take effect whenever the state of the - * parent surface is applied. - * - * If more than one set_position request is invoked by the client before - * the commit of the parent surface, the position of a new request always - * replaces the scheduled position from any previous request. - * * The initial position is 0, 0. + * + * Position is double-buffered state on the parent surface, see + * wl_subsurface and wl_surface.commit for more information. */ static inline void wl_subsurface_set_position(struct wl_subsurface *wl_subsurface, int32_t x, int32_t y) @@ -6375,13 +6555,11 @@ wl_subsurface_set_position(struct wl_subsurface *wl_subsurface, int32_t x, int32 * parent surface. Using any other surface, including this sub-surface, * will cause a protocol error. * - * The z-order is double-buffered. Requests are handled in order and - * applied immediately to a pending state. The final pending state is - * copied to the active state the next time the state of the parent - * surface is applied. - * * A new sub-surface is initially added as the top-most in the stack * of its siblings and parent. + * + * Z-order is double-buffered state on the parent surface, see + * wl_subsurface and wl_surface.commit for more information. */ static inline void wl_subsurface_place_above(struct wl_subsurface *wl_subsurface, struct wl_surface *sibling) @@ -6394,6 +6572,7 @@ wl_subsurface_place_above(struct wl_subsurface *wl_subsurface, struct wl_surface * @ingroup iface_wl_subsurface * * The sub-surface is placed just below the reference surface. + * * See wl_subsurface.place_above. */ static inline void @@ -6407,18 +6586,9 @@ wl_subsurface_place_below(struct wl_subsurface *wl_subsurface, struct wl_surface * @ingroup iface_wl_subsurface * * Change the commit behaviour of the sub-surface to synchronized - * mode, also described as the parent dependent mode. + * mode. * - * In synchronized mode, wl_surface.commit on a sub-surface will - * accumulate the committed state in a cache, but the state will - * not be applied and hence will not change the compositor output. - * The cached state is applied to the sub-surface immediately after - * the parent surface's state is applied. This ensures atomic - * updates of the parent and all its synchronized sub-surfaces. - * Applying the cached state will invalidate the cache, so further - * parent surface commits do not (re-)apply old state. - * - * See wl_subsurface for the recursive effect of this mode. + * See wl_subsurface and wl_surface.commit for more information. */ static inline void wl_subsurface_set_sync(struct wl_subsurface *wl_subsurface) @@ -6431,24 +6601,9 @@ wl_subsurface_set_sync(struct wl_subsurface *wl_subsurface) * @ingroup iface_wl_subsurface * * Change the commit behaviour of the sub-surface to desynchronized - * mode, also described as independent or freely running mode. + * mode. * - * In desynchronized mode, wl_surface.commit on a sub-surface will - * apply the pending state directly, without caching, as happens - * normally with a wl_surface. Calling wl_surface.commit on the - * parent surface has no effect on the sub-surface's wl_surface - * state. This mode allows a sub-surface to be updated on its own. - * - * If cached state exists when wl_surface.commit is called in - * desynchronized mode, the pending state is added to the cached - * state, and applied as a whole. This invalidates the cache. - * - * Note: even if a sub-surface is set to desynchronized, a parent - * sub-surface may override it to behave as synchronized. For details, - * see wl_subsurface. - * - * If a surface's parent surface behaves as desynchronized, then - * the cached state is applied on set_desync. + * See wl_subsurface and wl_surface.commit for more information. */ static inline void wl_subsurface_set_desync(struct wl_subsurface *wl_subsurface) diff --git a/include/fennec/platform/linux/wayland/lib/headers/xdg-shell-client-protocols.h b/include/fennec/platform/linux/wayland/lib/headers/xdg-shell-client-protocols.h index 9496b9f..9d141b6 100644 --- a/include/fennec/platform/linux/wayland/lib/headers/xdg-shell-client-protocols.h +++ b/include/fennec/platform/linux/wayland/lib/headers/xdg-shell-client-protocols.h @@ -1,4 +1,4 @@ -/* Generated by wayland-scanner 1.24.0 */ +/* Generated by wayland-scanner 1.25.0 */ #ifndef XDG_SHELL_CLIENT_PROTOCOL_H #define XDG_SHELL_CLIENT_PROTOCOL_H diff --git a/include/fennec/platform/linux/wayland/lib/protocols/wayland.xml b/include/fennec/platform/linux/wayland/lib/protocols/wayland.xml index bee74a1..513b8fd 100644 --- a/include/fennec/platform/linux/wayland/lib/protocols/wayland.xml +++ b/include/fennec/platform/linux/wayland/lib/protocols/wayland.xml @@ -36,47 +36,47 @@ - The sync request asks the server to emit the 'done' event - on the returned wl_callback object. Since requests are - handled in-order and events are delivered in-order, this can - be used as a barrier to ensure all previous requests and the - resulting events have been handled. + The sync request asks the server to emit the 'done' event + on the returned wl_callback object. Since requests are + handled in-order and events are delivered in-order, this can + be used as a barrier to ensure all previous requests and the + resulting events have been handled. - The object returned by this request will be destroyed by the - compositor after the callback is fired and as such the client must not - attempt to use it after that point. + The object returned by this request will be destroyed by the + compositor after the callback is fired and as such the client must not + attempt to use it after that point. - The callback_data passed in the callback is undefined and should be ignored. + The callback_data passed in the callback is undefined and should be ignored. + summary="callback object for the sync request"/> - This request creates a registry object that allows the client - to list and bind the global objects available from the - compositor. + This request creates a registry object that allows the client + to list and bind the global objects available from the + compositor. - It should be noted that the server side resources consumed in - response to a get_registry request can only be released when the - client disconnects, not when the client side proxy is destroyed. - Therefore, clients should invoke get_registry as infrequently as - possible to avoid wasting memory. + It should be noted that the server side resources consumed in + response to a get_registry request can only be released when the + client disconnects, not when the client side proxy is destroyed. + Therefore, clients should invoke get_registry as infrequently as + possible to avoid wasting memory. + summary="global registry object"/> - The error event is sent out when a fatal (non-recoverable) - error has occurred. The object_id argument is the object - where the error occurred, most often in response to a request - to that object. The code identifies the error and is defined - by the object interface. As such, each interface defines its - own set of error codes. The message is a brief description - of the error, for (debugging) convenience. + The error event is sent out when a fatal (non-recoverable) + error has occurred. The object_id argument is the object + where the error occurred, most often in response to a request + to that object. The code identifies the error and is defined + by the object interface. As such, each interface defines its + own set of error codes. The message is a brief description + of the error, for (debugging) convenience. @@ -85,26 +85,26 @@ - These errors are global and can be emitted in response to any - server request. + These errors are global and can be emitted in response to any + server request. + summary="server couldn't find object"/> + summary="method doesn't exist on the specified interface or malformed request"/> + summary="server is out of memory"/> + summary="implementation error in compositor"/> - This event is used internally by the object ID management - logic. When a client deletes an object that it had created, - the server will send this event to acknowledge that it has - seen the delete request. When the client receives this event, - it will know that it can safely reuse the object ID. + This event is used internally by the object ID management + logic. When a client deletes an object that it had created, + the server will send this event to acknowledge that it has + seen the delete request. When the client receives this event, + it will know that it can safely reuse the object ID. @@ -136,8 +136,8 @@ - Binds a new, client-created object to the server using the - specified name as the identifier. + Binds a new, client-created object to the server using the + specified name as the identifier. @@ -145,11 +145,11 @@ - Notify the client of global objects. + Notify the client of global objects. - The event notifies the client that a global object with - the given name is now available, and it implements the - given version of the given interface. + The event notifies the client that a global object with + the given name is now available, and it implements the + given version of the given interface. @@ -158,22 +158,22 @@ - Notify the client of removed global objects. + Notify the client of removed global objects. - This event notifies the client that the global identified - by name is no longer available. If the client bound to - the global using the bind request, the client should now - destroy that object. + This event notifies the client that the global identified + by name is no longer available. If the client bound to + the global using the bind request, the client should now + destroy that object. - The object remains valid and requests to the object will be - ignored until the client destroys it, to avoid races between - the global going away and a client sending a request to it. + The object remains valid and requests to the object will be + ignored until the client destroys it, to avoid races between + the global going away and a client sending a request to it. - + Clients can handle the 'done' event to get notified when the related request is done. @@ -184,13 +184,13 @@ - Notify the client when the related request is done. + Notify the client when the related request is done. - + A compositor. This object is a singleton global. The compositor is in charge of combining the contents of multiple @@ -199,17 +199,25 @@ - Ask the compositor to create a new surface. + Ask the compositor to create a new surface. - Ask the compositor to create a new region. + Ask the compositor to create a new region. + + + + + + This request destroys the wl_compositor. This has no effect on any other objects. + + @@ -225,17 +233,17 @@ - Create a wl_buffer object from the pool. + Create a wl_buffer object from the pool. - The buffer is created offset bytes into the pool and has - width and height as specified. The stride argument specifies - the number of bytes from the beginning of one row to the beginning - of the next. The format is the pixel format of the buffer and - must be one of those advertised through the wl_shm.format event. + The buffer is created offset bytes into the pool and has + width and height as specified. The stride argument specifies + the number of bytes from the beginning of one row to the beginning + of the next. The format is the pixel format of the buffer and + must be one of those advertised through the wl_shm.format event. - A buffer will keep a reference to the pool it was created from - so it is valid to destroy the pool immediately after creating - a buffer from it. + A buffer will keep a reference to the pool it was created from + so it is valid to destroy the pool immediately after creating + a buffer from it. @@ -247,26 +255,26 @@ - Destroy the shared memory pool. + Destroy the shared memory pool. - The mmapped memory will be released when all - buffers that have been created from this pool - are gone. + The mmapped memory will be released when all + buffers that have been created from this pool + are gone. - This request will cause the server to remap the backing memory - for the pool from the file descriptor passed when the pool was - created, but using the new size. This request can only be - used to make the pool bigger. + This request will cause the server to remap the backing memory + for the pool from the file descriptor passed when the pool was + created, but using the new size. This request can only be + used to make the pool bigger. - This request only changes the amount of bytes that are mmapped - by the server and does not touch the file corresponding to the - file descriptor passed at creation time. It is the client's - responsibility to ensure that the file is at least as big as - the new pool size. + This request only changes the amount of bytes that are mmapped + by the server and does not touch the file corresponding to the + file descriptor passed at creation time. It is the client's + responsibility to ensure that the file is at least as big as + the new pool size. @@ -287,7 +295,7 @@ - These errors can be emitted in response to wl_shm requests. + These errors can be emitted in response to wl_shm requests. @@ -296,21 +304,22 @@ - This describes the memory layout of an individual pixel. + This describes the memory layout of an individual pixel. - All renderers should support argb8888 and xrgb8888 but any other - formats are optional and may not be supported by the particular - renderer in use. + All renderers should support argb8888 and xrgb8888 but any other + formats are optional and may not be supported by the particular + renderer in use. - The drm format codes match the macros defined in drm_fourcc.h, except - argb8888 and xrgb8888. The formats actually supported by the compositor - will be reported by the format event. + The drm format codes match the macros defined in drm_fourcc.h, except + argb8888 and xrgb8888. The formats actually supported by the compositor + will be reported by the format event. See drm_fourcc.h for more detailed + format descriptions. - For all wl_shm formats and unless specified in another protocol - extension, pre-multiplied alpha is used for pixel values. + For all wl_shm formats and unless specified in another protocol + extension, pre-multiplied alpha is used for pixel values. + run the automated script that keeps it in sync with drm_fourcc.h. --> @@ -434,15 +443,35 @@ + + + + + + + + + + + + + + + + + + + + - Create a new wl_shm_pool object. + Create a new wl_shm_pool object. - The pool can be used to create shared memory based buffer - objects. The server will mmap size bytes of the passed file - descriptor, to use as backing memory for the pool. + The pool can be used to create shared memory based buffer + objects. The server will mmap size bytes of the passed file + descriptor, to use as backing memory for the pool. @@ -451,9 +480,13 @@ - Informs the client about a valid pixel format that - can be used for buffers. Known formats include - argb8888 and xrgb8888. + Informs the client about a valid pixel format that + can be used for buffers. Known formats include + argb8888 and xrgb8888. + + Extensions to drm_fourcc.h (or the format enum) do not require + increasing the wl_shm version; as a result, clients may receive format + codes which were not in the list at the time the client was made. @@ -462,15 +495,15 @@ - Using this request a client can tell the server that it is not going to - use the shm object anymore. + Using this request a client can tell the server that it is not going to + use the shm object anymore. - Objects created via this interface remain unaffected. + Objects created via this interface remain unaffected. - + A buffer provides the content for a wl_surface. Buffers are created through factory interfaces such as wl_shm, wp_linux_buffer_params @@ -491,34 +524,34 @@ - Destroy a buffer. If and how you need to release the backing - storage is defined by the buffer factory interface. + Destroy a buffer. If and how you need to release the backing + storage is defined by the buffer factory interface. - For possible side-effects to a surface, see wl_surface.attach. + For possible side-effects to a surface, see wl_surface.attach. - Sent when this wl_buffer is no longer used by the compositor. + Sent when this wl_buffer is no longer used by the compositor. - For more information on when release events may or may not be sent, - and what consequences it has, please see the description of - wl_surface.attach. + For more information on when release events may or may not be sent, + and what consequences it has, please see the description of + wl_surface.attach. - If a client receives a release event before the frame callback - requested in the same wl_surface.commit that attaches this - wl_buffer to a surface, then the client is immediately free to - reuse the buffer and its backing storage, and does not need a - second buffer for the next surface content update. Typically - this is possible, when the compositor maintains a copy of the - wl_surface contents, e.g. as a GL texture. This is an important - optimization for GL(ES) compositors with wl_shm clients. + If a client receives a release event before the frame callback + requested in the same wl_surface.commit that attaches this + wl_buffer to a surface, then the client is immediately free to + reuse the buffer and its backing storage, and does not need a + second buffer for the next surface content update. Typically + this is possible, when the compositor maintains a copy of the + wl_surface contents, e.g. as a GL texture. This is an important + optimization for GL(ES) compositors with wl_shm clients. - + A wl_data_offer represents a piece of data offered for transfer by another client (the source client). It is used by the @@ -530,31 +563,31 @@ + summary="finish request was called untimely"/> + summary="action mask contains invalid values"/> + summary="action argument has an invalid value"/> + summary="offer doesn't accept this request"/> - Indicate that the client can accept the given mime type, or - NULL for not accepted. + Indicate that the client can accept the given mime type, or + NULL for not accepted. - For objects of version 2 or older, this request is used by the - client to give feedback whether the client can receive the given - mime type, or NULL if none is accepted; the feedback does not - determine whether the drag-and-drop operation succeeds or not. + For objects of version 2 or older, this request is used by the + client to give feedback whether the client can receive the given + mime type, or NULL if none is accepted; the feedback does not + determine whether the drag-and-drop operation succeeds or not. - For objects of version 3 or newer, this request determines the - final result of the drag-and-drop operation. If the end result - is that no mime types were accepted, the drag-and-drop operation - will be cancelled and the corresponding drag source will receive - wl_data_source.cancelled. Clients may still use this event in - conjunction with wl_data_source.action for feedback. + For objects of version 3 or newer, this request determines the + final result of the drag-and-drop operation. If the end result + is that no mime types were accepted, the drag-and-drop operation + will be cancelled and the corresponding drag source will receive + wl_data_source.cancelled. Clients may still use this event in + conjunction with wl_data_source.action for feedback. @@ -562,21 +595,21 @@ - To transfer the offered data, the client issues this request - and indicates the mime type it wants to receive. The transfer - happens through the passed file descriptor (typically created - with the pipe system call). The source client writes the data - in the mime type representation requested and then closes the - file descriptor. + To transfer the offered data, the client issues this request + and indicates the mime type it wants to receive. The transfer + happens through the passed file descriptor (typically created + with the pipe system call). The source client writes the data + in the mime type representation requested and then closes the + file descriptor. - The receiving client reads from the read end of the pipe until - EOF and then closes its end, at which point the transfer is - complete. + The receiving client reads from the read end of the pipe until + EOF and then closes its end, at which point the transfer is + complete. - This request may happen multiple times for different mime types, - both before and after wl_data_device.drop. Drag-and-drop destination - clients may preemptively fetch data or examine it more closely to - determine acceptance. + This request may happen multiple times for different mime types, + both before and after wl_data_device.drop. Drag-and-drop destination + clients may preemptively fetch data or examine it more closely to + determine acceptance. @@ -584,14 +617,14 @@ - Destroy the data offer. + Destroy the data offer. - Sent immediately after creating the wl_data_offer object. One - event per offered mime type. + Sent immediately after creating the wl_data_offer object. One + event per offered mime type. @@ -600,118 +633,118 @@ - Notifies the compositor that the drag destination successfully - finished the drag-and-drop operation. + Notifies the compositor that the drag destination successfully + finished the drag-and-drop operation. - Upon receiving this request, the compositor will emit - wl_data_source.dnd_finished on the drag source client. + Upon receiving this request, the compositor will emit + wl_data_source.dnd_finished on the drag source client. - It is a client error to perform other requests than - wl_data_offer.destroy after this one. It is also an error to perform - this request after a NULL mime type has been set in - wl_data_offer.accept or no action was received through - wl_data_offer.action. + It is a client error to perform other requests than + wl_data_offer.destroy after this one. It is also an error to perform + this request after a NULL mime type has been set in + wl_data_offer.accept or no action was received through + wl_data_offer.action. - If wl_data_offer.finish request is received for a non drag and drop - operation, the invalid_finish protocol error is raised. + If wl_data_offer.finish request is received for a non drag and drop + operation, the invalid_finish protocol error is raised. - Sets the actions that the destination side client supports for - this operation. This request may trigger the emission of - wl_data_source.action and wl_data_offer.action events if the compositor - needs to change the selected action. + Sets the actions that the destination side client supports for + this operation. This request may trigger the emission of + wl_data_source.action and wl_data_offer.action events if the compositor + needs to change the selected action. - This request can be called multiple times throughout the - drag-and-drop operation, typically in response to wl_data_device.enter - or wl_data_device.motion events. + This request can be called multiple times throughout the + drag-and-drop operation, typically in response to wl_data_device.enter + or wl_data_device.motion events. - This request determines the final result of the drag-and-drop - operation. If the end result is that no action is accepted, - the drag source will receive wl_data_source.cancelled. + This request determines the final result of the drag-and-drop + operation. If the end result is that no action is accepted, + the drag source will receive wl_data_source.cancelled. - The dnd_actions argument must contain only values expressed in the - wl_data_device_manager.dnd_actions enum, and the preferred_action - argument must only contain one of those values set, otherwise it - will result in a protocol error. + The dnd_actions argument must contain only values expressed in the + wl_data_device_manager.dnd_actions enum, and the preferred_action + argument must only contain one of those values set, otherwise it + will result in a protocol error. - While managing an "ask" action, the destination drag-and-drop client - may perform further wl_data_offer.receive requests, and is expected - to perform one last wl_data_offer.set_actions request with a preferred - action other than "ask" (and optionally wl_data_offer.accept) before - requesting wl_data_offer.finish, in order to convey the action selected - by the user. If the preferred action is not in the - wl_data_offer.source_actions mask, an error will be raised. + While managing an "ask" action, the destination drag-and-drop client + may perform further wl_data_offer.receive requests, and is expected + to perform one last wl_data_offer.set_actions request with a preferred + action other than "ask" (and optionally wl_data_offer.accept) before + requesting wl_data_offer.finish, in order to convey the action selected + by the user. If the preferred action is not in the + wl_data_offer.source_actions mask, an error will be raised. - If the "ask" action is dismissed (e.g. user cancellation), the client - is expected to perform wl_data_offer.destroy right away. + If the "ask" action is dismissed (e.g. user cancellation), the client + is expected to perform wl_data_offer.destroy right away. - This request can only be made on drag-and-drop offers, a protocol error - will be raised otherwise. + This request can only be made on drag-and-drop offers, a protocol error + will be raised otherwise. + enum="wl_data_device_manager.dnd_action"/> + enum="wl_data_device_manager.dnd_action"/> - This event indicates the actions offered by the data source. It - will be sent immediately after creating the wl_data_offer object, - or anytime the source side changes its offered actions through - wl_data_source.set_actions. + This event indicates the actions offered by the data source. It + will be sent immediately after creating the wl_data_offer object, + or anytime the source side changes its offered actions through + wl_data_source.set_actions. + enum="wl_data_device_manager.dnd_action"/> - This event indicates the action selected by the compositor after - matching the source/destination side actions. Only one action (or - none) will be offered here. + This event indicates the action selected by the compositor after + matching the source/destination side actions. Only one action (or + none) will be offered here. - This event can be emitted multiple times during the drag-and-drop - operation in response to destination side action changes through - wl_data_offer.set_actions. + This event can be emitted multiple times during the drag-and-drop + operation in response to destination side action changes through + wl_data_offer.set_actions. - This event will no longer be emitted after wl_data_device.drop - happened on the drag-and-drop destination, the client must - honor the last action received, or the last preferred one set - through wl_data_offer.set_actions when handling an "ask" action. + This event will no longer be emitted after wl_data_device.drop + happened on the drag-and-drop destination, the client must + honor the last action received, or the last preferred one set + through wl_data_offer.set_actions when handling an "ask" action. - Compositors may also change the selected action on the fly, mainly - in response to keyboard modifier changes during the drag-and-drop - operation. + Compositors may also change the selected action on the fly, mainly + in response to keyboard modifier changes during the drag-and-drop + operation. - The most recent action received is always the valid one. Prior to - receiving wl_data_device.drop, the chosen action may change (e.g. - due to keyboard modifiers being pressed). At the time of receiving - wl_data_device.drop the drag-and-drop destination must honor the - last action received. + The most recent action received is always the valid one. Prior to + receiving wl_data_device.drop, the chosen action may change (e.g. + due to keyboard modifiers being pressed). At the time of receiving + wl_data_device.drop the drag-and-drop destination must honor the + last action received. - Action changes may still happen after wl_data_device.drop, - especially on "ask" actions, where the drag-and-drop destination - may choose another action afterwards. Action changes happening - at this stage are always the result of inter-client negotiation, the - compositor shall no longer be able to induce a different action. + Action changes may still happen after wl_data_device.drop, + especially on "ask" actions, where the drag-and-drop destination + may choose another action afterwards. Action changes happening + at this stage are always the result of inter-client negotiation, the + compositor shall no longer be able to induce a different action. - Upon "ask" actions, it is expected that the drag-and-drop destination - may potentially choose a different action and/or mime type, - based on wl_data_offer.source_actions and finally chosen by the - user (e.g. popping up a menu with the available options). The - final wl_data_offer.set_actions and wl_data_offer.accept requests - must happen before the call to wl_data_offer.finish. + Upon "ask" actions, it is expected that the drag-and-drop destination + may potentially choose a different action and/or mime type, + based on wl_data_offer.source_actions and finally chosen by the + user (e.g. popping up a menu with the available options). The + final wl_data_offer.set_actions and wl_data_offer.accept requests + must happen before the call to wl_data_offer.finish. + enum="wl_data_device_manager.dnd_action"/> - + The wl_data_source object is the source side of a wl_data_offer. It is created by the source client in a data transfer and @@ -721,41 +754,41 @@ + summary="action mask contains invalid values"/> + summary="source doesn't accept this request"/> - This request adds a mime type to the set of mime types - advertised to targets. Can be called several times to offer - multiple types. + This request adds a mime type to the set of mime types + advertised to targets. Can be called several times to offer + multiple types. - Destroy the data source. + Destroy the data source. - Sent when a target accepts pointer_focus or motion events. If - a target does not accept any of the offered types, type is NULL. + Sent when a target accepts pointer_focus or motion events. If + a target does not accept any of the offered types, type is NULL. - Used for feedback during drag-and-drop. + Used for feedback during drag-and-drop. - Request for data from the client. Send the data as the - specified mime type over the passed file descriptor, then - close it. + Request for data from the client. Send the data as the + specified mime type over the passed file descriptor, then + close it. @@ -763,26 +796,26 @@ - This data source is no longer valid. There are several reasons why - this could happen: + This data source is no longer valid. There are several reasons why + this could happen: - - The data source has been replaced by another data source. - - The drag-and-drop operation was performed, but the drop destination - did not accept any of the mime types offered through - wl_data_source.target. - - The drag-and-drop operation was performed, but the drop destination - did not select any of the actions present in the mask offered through - wl_data_source.action. - - The drag-and-drop operation was performed but didn't happen over a - surface. - - The compositor cancelled the drag-and-drop operation (e.g. compositor - dependent timeouts to avoid stale drag-and-drop transfers). + - The data source has been replaced by another data source. + - The drag-and-drop operation was performed, but the drop destination + did not accept any of the mime types offered through + wl_data_source.target. + - The drag-and-drop operation was performed, but the drop destination + did not select any of the actions present in the mask offered through + wl_data_source.action. + - The drag-and-drop operation was performed but didn't happen over a + surface. + - The compositor cancelled the drag-and-drop operation (e.g. compositor + dependent timeouts to avoid stale drag-and-drop transfers). - The client should clean up and destroy this data source. + The client should clean up and destroy this data source. - For objects of version 2 or older, wl_data_source.cancelled will - only be emitted if the data source was replaced by another data - source. + For objects of version 2 or older, wl_data_source.cancelled will + only be emitted if the data source was replaced by another data + source. @@ -790,83 +823,83 @@ - Sets the actions that the source side client supports for this - operation. This request may trigger wl_data_source.action and - wl_data_offer.action events if the compositor needs to change the - selected action. + Sets the actions that the source side client supports for this + operation. This request may trigger wl_data_source.action and + wl_data_offer.action events if the compositor needs to change the + selected action. - The dnd_actions argument must contain only values expressed in the - wl_data_device_manager.dnd_actions enum, otherwise it will result - in a protocol error. + The dnd_actions argument must contain only values expressed in the + wl_data_device_manager.dnd_actions enum, otherwise it will result + in a protocol error. - This request must be made once only, and can only be made on sources - used in drag-and-drop, so it must be performed before - wl_data_device.start_drag. Attempting to use the source other than - for drag-and-drop will raise a protocol error. + This request must be made once only, and can only be made on sources + used in drag-and-drop, so it must be performed before + wl_data_device.start_drag. Attempting to use the source other than + for drag-and-drop will raise a protocol error. + enum="wl_data_device_manager.dnd_action"/> - The user performed the drop action. This event does not indicate - acceptance, wl_data_source.cancelled may still be emitted afterwards - if the drop destination does not accept any mime type. + The user performed the drop action. This event does not indicate + acceptance, wl_data_source.cancelled may still be emitted afterwards + if the drop destination does not accept any mime type. - However, this event might however not be received if the compositor - cancelled the drag-and-drop operation before this event could happen. + However, this event might however not be received if the compositor + cancelled the drag-and-drop operation before this event could happen. - Note that the data_source may still be used in the future and should - not be destroyed here. + Note that the data_source may still be used in the future and should + not be destroyed here. - The drop destination finished interoperating with this data - source, so the client is now free to destroy this data source and - free all associated data. + The drop destination finished interoperating with this data + source, so the client is now free to destroy this data source and + free all associated data. - If the action used to perform the operation was "move", the - source can now delete the transferred data. + If the action used to perform the operation was "move", the + source can now delete the transferred data. - This event indicates the action selected by the compositor after - matching the source/destination side actions. Only one action (or - none) will be offered here. + This event indicates the action selected by the compositor after + matching the source/destination side actions. Only one action (or + none) will be offered here. - This event can be emitted multiple times during the drag-and-drop - operation, mainly in response to destination side changes through - wl_data_offer.set_actions, and as the data device enters/leaves - surfaces. + This event can be emitted multiple times during the drag-and-drop + operation, mainly in response to destination side changes through + wl_data_offer.set_actions, and as the data device enters/leaves + surfaces. - It is only possible to receive this event after - wl_data_source.dnd_drop_performed if the drag-and-drop operation - ended in an "ask" action, in which case the final wl_data_source.action - event will happen immediately before wl_data_source.dnd_finished. + It is only possible to receive this event after + wl_data_source.dnd_drop_performed if the drag-and-drop operation + ended in an "ask" action, in which case the final wl_data_source.action + event will happen immediately before wl_data_source.dnd_finished. - Compositors may also change the selected action on the fly, mainly - in response to keyboard modifier changes during the drag-and-drop - operation. + Compositors may also change the selected action on the fly, mainly + in response to keyboard modifier changes during the drag-and-drop + operation. - The most recent action received is always the valid one. The chosen - action may change alongside negotiation (e.g. an "ask" action can turn - into a "move" operation), so the effects of the final action must - always be applied in wl_data_offer.dnd_finished. + The most recent action received is always the valid one. The chosen + action may change alongside negotiation (e.g. an "ask" action can turn + into a "move" operation), so the effects of the final action must + always be applied in wl_data_offer.dnd_finished. - Clients can trigger cursor surface changes from this point, so - they reflect the current action. + Clients can trigger cursor surface changes from this point, so + they reflect the current action. + enum="wl_data_device_manager.dnd_action"/> - + There is one wl_data_device per seat which can be obtained from the global wl_data_device_manager singleton. @@ -882,35 +915,35 @@ - This request asks the compositor to start a drag-and-drop - operation on behalf of the client. + This request asks the compositor to start a drag-and-drop + operation on behalf of the client. - The source argument is the data source that provides the data - for the eventual data transfer. If source is NULL, enter, leave - and motion events are sent only to the client that initiated the - drag and the client is expected to handle the data passing - internally. If source is destroyed, the drag-and-drop session will be - cancelled. + The source argument is the data source that provides the data + for the eventual data transfer. If source is NULL, enter, leave + and motion events are sent only to the client that initiated the + drag and the client is expected to handle the data passing + internally. If source is destroyed, the drag-and-drop session will be + cancelled. - The origin surface is the surface where the drag originates and - the client must have an active implicit grab that matches the - serial. + The origin surface is the surface where the drag originates and + the client must have an active implicit grab that matches the + serial. - The icon surface is an optional (can be NULL) surface that - provides an icon to be moved around with the cursor. Initially, - the top-left corner of the icon surface is placed at the cursor - hotspot, but subsequent wl_surface.offset requests can move the - relative position. Attach requests must be confirmed with - wl_surface.commit as usual. The icon surface is given the role of - a drag-and-drop icon. If the icon surface already has another role, - it raises a protocol error. + The icon surface is an optional (can be NULL) surface that + provides an icon to be moved around with the cursor. Initially, + the top-left corner of the icon surface is placed at the cursor + hotspot, but subsequent wl_surface.offset requests can move the + relative position. Attach requests must be confirmed with + wl_surface.commit as usual. The icon surface is given the role of + a drag-and-drop icon. If the icon surface already has another role, + it raises a protocol error. - The input region is ignored for wl_surfaces with the role of a - drag-and-drop icon. + The input region is ignored for wl_surfaces with the role of a + drag-and-drop icon. - The given source may not be used in any further set_selection or - start_drag requests. Attempting to reuse a previously-used source - may send a used_source error. + The given source may not be used in any further set_selection or + start_drag requests. Attempting to reuse a previously-used source + may send a used_source error. @@ -920,14 +953,14 @@ - This request asks the compositor to set the selection - to the data from the source on behalf of the client. + This request asks the compositor to set the selection + to the data from the source on behalf of the client. - To unset the selection, set the source to NULL. + To unset the selection, set the source to NULL. - The given source may not be used in any further set_selection or - start_drag requests. Attempting to reuse a previously-used source - may send a used_source error. + The given source may not be used in any further set_selection or + start_drag requests. Attempting to reuse a previously-used source + may send a used_source error. @@ -935,46 +968,46 @@ - The data_offer event introduces a new wl_data_offer object, - which will subsequently be used in either the - data_device.enter event (for drag-and-drop) or the - data_device.selection event (for selections). Immediately - following the data_device.data_offer event, the new data_offer - object will send out data_offer.offer events to describe the - mime types it offers. + The data_offer event introduces a new wl_data_offer object, + which will subsequently be used in either the + data_device.enter event (for drag-and-drop) or the + data_device.selection event (for selections). Immediately + following the data_device.data_offer event, the new data_offer + object will send out data_offer.offer events to describe the + mime types it offers. - This event is sent when an active drag-and-drop pointer enters - a surface owned by the client. The position of the pointer at - enter time is provided by the x and y arguments, in surface-local - coordinates. + This event is sent when an active drag-and-drop pointer enters + a surface owned by the client. The position of the pointer at + enter time is provided by the x and y arguments, in surface-local + coordinates. + summary="source data_offer object"/> - This event is sent when the drag-and-drop pointer leaves the - surface and the session ends. The client must destroy the - wl_data_offer introduced at enter time at this point. + This event is sent when the drag-and-drop pointer leaves the + surface and the session ends. The client must destroy the + wl_data_offer introduced at enter time at this point. - This event is sent when the drag-and-drop pointer moves within - the currently focused surface. The new position of the pointer - is provided by the x and y arguments, in surface-local - coordinates. + This event is sent when the drag-and-drop pointer moves within + the currently focused surface. The new position of the pointer + is provided by the x and y arguments, in surface-local + coordinates. @@ -983,51 +1016,51 @@ - The event is sent when a drag-and-drop operation is ended - because the implicit grab is removed. + The event is sent when a drag-and-drop operation is ended + because the implicit grab is removed. - The drag-and-drop destination is expected to honor the last action - received through wl_data_offer.action, if the resulting action is - "copy" or "move", the destination can still perform - wl_data_offer.receive requests, and is expected to end all - transfers with a wl_data_offer.finish request. + The drag-and-drop destination is expected to honor the last action + received through wl_data_offer.action, if the resulting action is + "copy" or "move", the destination can still perform + wl_data_offer.receive requests, and is expected to end all + transfers with a wl_data_offer.finish request. - If the resulting action is "ask", the action will not be considered - final. The drag-and-drop destination is expected to perform one last - wl_data_offer.set_actions request, or wl_data_offer.destroy in order - to cancel the operation. + If the resulting action is "ask", the action will not be considered + final. The drag-and-drop destination is expected to perform one last + wl_data_offer.set_actions request, or wl_data_offer.destroy in order + to cancel the operation. - The selection event is sent out to notify the client of a new - wl_data_offer for the selection for this device. The - data_device.data_offer and the data_offer.offer events are - sent out immediately before this event to introduce the data - offer object. The selection event is sent to a client - immediately before receiving keyboard focus and when a new - selection is set while the client has keyboard focus. The - data_offer is valid until a new data_offer or NULL is received - or until the client loses keyboard focus. Switching surface with - keyboard focus within the same client doesn't mean a new selection - will be sent. The client must destroy the previous selection - data_offer, if any, upon receiving this event. + The selection event is sent out to notify the client of a new + wl_data_offer for the selection for this device. The + data_device.data_offer and the data_offer.offer events are + sent out immediately before this event to introduce the data + offer object. The selection event is sent to a client + immediately before receiving keyboard focus and when a new + selection is set while the client has keyboard focus. The + data_offer is valid until a new data_offer or NULL is received + or until the client loses keyboard focus. Switching surface with + keyboard focus within the same client doesn't mean a new selection + will be sent. The client must destroy the previous selection + data_offer, if any, upon receiving this event. + summary="selection data_offer object"/> - This request destroys the data device. + This request destroys the data device. - + The wl_data_device_manager is a singleton global object that provides access to inter-client data transfer mechanisms such as @@ -1043,14 +1076,14 @@ - Create a new data source. + Create a new data source. - Create a new data device for a given seat. + Create a new data device for a given seat. @@ -1060,35 +1093,44 @@ - This is a bitmask of the available/preferred actions in a - drag-and-drop operation. + This is a bitmask of the available/preferred actions in a + drag-and-drop operation. - In the compositor, the selected action is a result of matching the - actions offered by the source and destination sides. "action" events - with a "none" action will be sent to both source and destination if - there is no match. All further checks will effectively happen on - (source actions ∩ destination actions). + In the compositor, the selected action is a result of matching the + actions offered by the source and destination sides. "action" events + with a "none" action will be sent to both source and destination if + there is no match. All further checks will effectively happen on + (source actions ∩ destination actions). - In addition, compositors may also pick different actions in - reaction to key modifiers being pressed. One common design that - is used in major toolkits (and the behavior recommended for - compositors) is: + In addition, compositors may also pick different actions in + reaction to key modifiers being pressed. One common design that + is used in major toolkits (and the behavior recommended for + compositors) is: - - If no modifiers are pressed, the first match (in bit order) - will be used. - - Pressing Shift selects "move", if enabled in the mask. - - Pressing Control selects "copy", if enabled in the mask. + - If no modifiers are pressed, the first match (in bit order) + will be used. + - Pressing Shift selects "move", if enabled in the mask. + - Pressing Control selects "copy", if enabled in the mask. - Behavior beyond that is considered implementation-dependent. - Compositors may for example bind other modifiers (like Alt/Meta) - or drags initiated with other buttons than BTN_LEFT to specific - actions (e.g. "ask"). + Behavior beyond that is considered implementation-dependent. + Compositors may for example bind other modifiers (like Alt/Meta) + or drags initiated with other buttons than BTN_LEFT to specific + actions (e.g. "ask"). + + + + + + This request destroys the wl_data_device_manager. This has no effect on any other + objects. + + @@ -1110,11 +1152,11 @@ - Create a shell surface for an existing surface. This gives - the wl_surface the role of a shell surface. If the wl_surface - already has another role, it raises a protocol error. + Create a shell surface for an existing surface. This gives + the wl_surface the role of a shell surface. If the wl_surface + already has another role, it raises a protocol error. - Only one shell surface can be associated with a given surface. + Only one shell surface can be associated with a given surface. @@ -1138,19 +1180,19 @@ - A client must respond to a ping event with a pong request or - the client may be deemed unresponsive. + A client must respond to a ping event with a pong request or + the client may be deemed unresponsive. - Start a pointer-driven move of the surface. + Start a pointer-driven move of the surface. - This request must be used in response to a button press event. - The server may ignore move requests depending on the state of - the surface (e.g. fullscreen or maximized). + This request must be used in response to a button press event. + The server may ignore move requests depending on the state of + the surface (e.g. fullscreen or maximized). @@ -1158,10 +1200,10 @@ - These values are used to indicate which edge of a surface - is being dragged in a resize operation. The server may - use this information to adapt its behavior, e.g. choose - an appropriate cursor image. + These values are used to indicate which edge of a surface + is being dragged in a resize operation. The server may + use this information to adapt its behavior, e.g. choose + an appropriate cursor image. @@ -1176,11 +1218,11 @@ - Start a pointer-driven resizing of the surface. + Start a pointer-driven resizing of the surface. - This request must be used in response to a button press event. - The server may ignore resize requests depending on the state of - the surface (e.g. fullscreen or maximized). + This request must be used in response to a button press event. + The server may ignore resize requests depending on the state of + the surface (e.g. fullscreen or maximized). @@ -1189,29 +1231,29 @@ - Map the surface as a toplevel surface. + Map the surface as a toplevel surface. - A toplevel surface is not fullscreen, maximized or transient. + A toplevel surface is not fullscreen, maximized or transient. - These flags specify details of the expected behaviour - of transient surfaces. Used in the set_transient request. + These flags specify details of the expected behaviour + of transient surfaces. Used in the set_transient request. - Map the surface relative to an existing surface. + Map the surface relative to an existing surface. - The x and y arguments specify the location of the upper left - corner of the surface relative to the upper left corner of the - parent surface, in surface-local coordinates. + The x and y arguments specify the location of the upper left + corner of the surface relative to the upper left corner of the + parent surface, in surface-local coordinates. - The flags argument controls details of the transient behaviour. + The flags argument controls details of the transient behaviour. @@ -1221,9 +1263,9 @@ - Hints to indicate to the compositor how to deal with a conflict - between the dimensions of the surface and the dimensions of the - output. The compositor is free to ignore this parameter. + Hints to indicate to the compositor how to deal with a conflict + between the dimensions of the surface and the dimensions of the + output. The compositor is free to ignore this parameter. @@ -1233,67 +1275,67 @@ - Map the surface as a fullscreen surface. + Map the surface as a fullscreen surface. - If an output parameter is given then the surface will be made - fullscreen on that output. If the client does not specify the - output then the compositor will apply its policy - usually - choosing the output on which the surface has the biggest surface - area. + If an output parameter is given then the surface will be made + fullscreen on that output. If the client does not specify the + output then the compositor will apply its policy - usually + choosing the output on which the surface has the biggest surface + area. - The client may specify a method to resolve a size conflict - between the output size and the surface size - this is provided - through the method parameter. + The client may specify a method to resolve a size conflict + between the output size and the surface size - this is provided + through the method parameter. - The framerate parameter is used only when the method is set - to "driver", to indicate the preferred framerate. A value of 0 - indicates that the client does not care about framerate. The - framerate is specified in mHz, that is framerate of 60000 is 60Hz. + The framerate parameter is used only when the method is set + to "driver", to indicate the preferred framerate. A value of 0 + indicates that the client does not care about framerate. The + framerate is specified in mHz, that is framerate of 60000 is 60Hz. - A method of "scale" or "driver" implies a scaling operation of - the surface, either via a direct scaling operation or a change of - the output mode. This will override any kind of output scaling, so - that mapping a surface with a buffer size equal to the mode can - fill the screen independent of buffer_scale. + A method of "scale" or "driver" implies a scaling operation of + the surface, either via a direct scaling operation or a change of + the output mode. This will override any kind of output scaling, so + that mapping a surface with a buffer size equal to the mode can + fill the screen independent of buffer_scale. - A method of "fill" means we don't scale up the buffer, however - any output scale is applied. This means that you may run into - an edge case where the application maps a buffer with the same - size of the output mode but buffer_scale 1 (thus making a - surface larger than the output). In this case it is allowed to - downscale the results to fit the screen. + A method of "fill" means we don't scale up the buffer, however + any output scale is applied. This means that you may run into + an edge case where the application maps a buffer with the same + size of the output mode but buffer_scale 1 (thus making a + surface larger than the output). In this case it is allowed to + downscale the results to fit the screen. - The compositor must reply to this request with a configure event - with the dimensions for the output on which the surface will - be made fullscreen. + The compositor must reply to this request with a configure event + with the dimensions for the output on which the surface will + be made fullscreen. + summary="output on which the surface is to be fullscreen"/> - Map the surface as a popup. + Map the surface as a popup. - A popup surface is a transient surface with an added pointer - grab. + A popup surface is a transient surface with an added pointer + grab. - An existing implicit grab will be changed to owner-events mode, - and the popup grab will continue after the implicit grab ends - (i.e. releasing the mouse button does not cause the popup to - be unmapped). + An existing implicit grab will be changed to owner-events mode, + and the popup grab will continue after the implicit grab ends + (i.e. releasing the mouse button does not cause the popup to + be unmapped). - The popup grab continues until the window is destroyed or a - mouse button is pressed in any other client's window. A click - in any of the client's surfaces is reported as normal, however, - clicks in other clients' surfaces will be discarded and trigger - the callback. + The popup grab continues until the window is destroyed or a + mouse button is pressed in any other client's window. A click + in any of the client's surfaces is reported as normal, however, + clicks in other clients' surfaces will be discarded and trigger + the callback. - The x and y arguments specify the location of the upper left - corner of the surface relative to the upper left corner of the - parent surface, in surface-local coordinates. + The x and y arguments specify the location of the upper left + corner of the surface relative to the upper left corner of the + parent surface, in surface-local coordinates. @@ -1305,81 +1347,81 @@ - Map the surface as a maximized surface. + Map the surface as a maximized surface. - If an output parameter is given then the surface will be - maximized on that output. If the client does not specify the - output then the compositor will apply its policy - usually - choosing the output on which the surface has the biggest surface - area. + If an output parameter is given then the surface will be + maximized on that output. If the client does not specify the + output then the compositor will apply its policy - usually + choosing the output on which the surface has the biggest surface + area. - The compositor will reply with a configure event telling - the expected new surface size. The operation is completed - on the next buffer attach to this surface. + The compositor will reply with a configure event telling + the expected new surface size. The operation is completed + on the next buffer attach to this surface. - A maximized surface typically fills the entire output it is - bound to, except for desktop elements such as panels. This is - the main difference between a maximized shell surface and a - fullscreen shell surface. + A maximized surface typically fills the entire output it is + bound to, except for desktop elements such as panels. This is + the main difference between a maximized shell surface and a + fullscreen shell surface. - The details depend on the compositor implementation. + The details depend on the compositor implementation. + summary="output on which the surface is to be maximized"/> - Set a short title for the surface. + Set a short title for the surface. - This string may be used to identify the surface in a task bar, - window list, or other user interface elements provided by the - compositor. + This string may be used to identify the surface in a task bar, + window list, or other user interface elements provided by the + compositor. - The string must be encoded in UTF-8. + The string must be encoded in UTF-8. - Set a class for the surface. + Set a class for the surface. - The surface class identifies the general class of applications - to which the surface belongs. A common convention is to use the - file name (or the full path if it is a non-standard location) of - the application's .desktop file as the class. + The surface class identifies the general class of applications + to which the surface belongs. A common convention is to use the + file name (or the full path if it is a non-standard location) of + the application's .desktop file as the class. - Ping a client to check if it is receiving events and sending - requests. A client is expected to reply with a pong request. + Ping a client to check if it is receiving events and sending + requests. A client is expected to reply with a pong request. - The configure event asks the client to resize its surface. + The configure event asks the client to resize its surface. - The size is a hint, in the sense that the client is free to - ignore it if it doesn't resize, pick a smaller size (to - satisfy aspect ratio or resize in steps of NxM pixels). + The size is a hint, in the sense that the client is free to + ignore it if it doesn't resize, pick a smaller size (to + satisfy aspect ratio or resize in steps of NxM pixels). - The edges parameter provides a hint about how the surface - was resized. The client may use this information to decide - how to adjust its content to the new size (e.g. a scrolling - area might adjust its content position to leave the viewable - content unmoved). + The edges parameter provides a hint about how the surface + was resized. The client may use this information to decide + how to adjust its content to the new size (e.g. a scrolling + area might adjust its content position to leave the viewable + content unmoved). - The client is free to dismiss all but the last configure - event it received. + The client is free to dismiss all but the last configure + event it received. - The width and height arguments specify the size of the window - in surface-local coordinates. + The width and height arguments specify the size of the window + in surface-local coordinates. @@ -1388,14 +1430,14 @@ - The popup_done event is sent out when a popup grab is broken, - that is, when the user clicks a surface that doesn't belong - to the client owning the popup surface. + The popup_done event is sent out when a popup grab is broken, + that is, when the user clicks a surface that doesn't belong + to the client owning the popup surface. - + A surface is a rectangular area that may be displayed on zero or more outputs, and shown any number of times at the compositor's @@ -1443,119 +1485,122 @@ - These errors can be emitted in response to wl_surface requests. + These errors can be emitted in response to wl_surface requests. + summary="surface was destroyed before its role object"/> + - Deletes the surface and invalidates its object ID. + Deletes the surface and invalidates its object ID. - Set a buffer as the content of this surface. + Set a buffer as the content of this surface. - The new size of the surface is calculated based on the buffer - size transformed by the inverse buffer_transform and the - inverse buffer_scale. This means that at commit time the supplied - buffer size must be an integer multiple of the buffer_scale. If - that's not the case, an invalid_size error is sent. + The new size of the surface is calculated based on the buffer + size transformed by the inverse buffer_transform and the + inverse buffer_scale. This means that at commit time the supplied + buffer size must be an integer multiple of the buffer_scale. If + that's not the case, an invalid_size error is sent. - The x and y arguments specify the location of the new pending - buffer's upper left corner, relative to the current buffer's upper - left corner, in surface-local coordinates. In other words, the - x and y, combined with the new surface size define in which - directions the surface's size changes. Setting anything other than 0 - as x and y arguments is discouraged, and should instead be replaced - with using the separate wl_surface.offset request. + The x and y arguments specify the location of the new pending + buffer's upper left corner, relative to the current buffer's upper + left corner, in surface-local coordinates. In other words, the + x and y, combined with the new surface size define in which + directions the surface's size changes. Setting anything other than 0 + as x and y arguments is discouraged, and should instead be replaced + with using the separate wl_surface.offset request. - When the bound wl_surface version is 5 or higher, passing any - non-zero x or y is a protocol violation, and will result in an - 'invalid_offset' error being raised. The x and y arguments are ignored - and do not change the pending state. To achieve equivalent semantics, - use wl_surface.offset. + When the bound wl_surface version is 5 or higher, passing any + non-zero x or y is a protocol violation, and will result in an + 'invalid_offset' error being raised. The x and y arguments are ignored + and do not change the pending state. To achieve equivalent semantics, + use wl_surface.offset. - Surface contents are double-buffered state, see wl_surface.commit. + Surface contents are double-buffered state, see wl_surface.commit. - The initial surface contents are void; there is no content. - wl_surface.attach assigns the given wl_buffer as the pending - wl_buffer. wl_surface.commit makes the pending wl_buffer the new - surface contents, and the size of the surface becomes the size - calculated from the wl_buffer, as described above. After commit, - there is no pending buffer until the next attach. + The initial surface contents are void; there is no content. + wl_surface.attach assigns the given wl_buffer as the pending + wl_buffer. wl_surface.commit makes the pending wl_buffer the new + surface contents, and the size of the surface becomes the size + calculated from the wl_buffer, as described above. After commit, + there is no pending buffer until the next attach. - Committing a pending wl_buffer allows the compositor to read the - pixels in the wl_buffer. The compositor may access the pixels at - any time after the wl_surface.commit request. When the compositor - will not access the pixels anymore, it will send the - wl_buffer.release event. Only after receiving wl_buffer.release, - the client may reuse the wl_buffer. A wl_buffer that has been - attached and then replaced by another attach instead of committed - will not receive a release event, and is not used by the - compositor. + Committing a pending wl_buffer allows the compositor to read the + pixels in the wl_buffer. The compositor may access the pixels at + any time after the wl_surface.commit request. When the compositor + will not access the pixels anymore, it will send the + wl_buffer.release event. Only after receiving wl_buffer.release, + the client may reuse the wl_buffer. A wl_buffer that has been + attached and then replaced by another attach instead of committed + will not receive a release event, and is not used by the + compositor. - If a pending wl_buffer has been committed to more than one wl_surface, - the delivery of wl_buffer.release events becomes undefined. A well - behaved client should not rely on wl_buffer.release events in this - case. Alternatively, a client could create multiple wl_buffer objects - from the same backing storage or use a protocol extension providing - per-commit release notifications. + If a pending wl_buffer has been committed to more than one wl_surface, + the delivery of wl_buffer.release events becomes undefined. A well + behaved client should not rely on wl_buffer.release events in this + case. Instead, clients hitting this case should use + wl_surface.get_release or use a protocol extension providing per-commit + release notifications (if none of these options are available, a + fallback can be implemented by creating multiple wl_buffer objects from + the same backing storage). - Destroying the wl_buffer after wl_buffer.release does not change - the surface contents. Destroying the wl_buffer before wl_buffer.release - is allowed as long as the underlying buffer storage isn't re-used (this - can happen e.g. on client process termination). However, if the client - destroys the wl_buffer before receiving the wl_buffer.release event and - mutates the underlying buffer storage, the surface contents become - undefined immediately. + Destroying the wl_buffer after wl_buffer.release does not change + the surface contents. Destroying the wl_buffer before wl_buffer.release + is allowed as long as the underlying buffer storage isn't re-used (this + can happen e.g. on client process termination). However, if the client + destroys the wl_buffer before receiving the wl_buffer.release event and + mutates the underlying buffer storage, the surface contents become + undefined immediately. - If wl_surface.attach is sent with a NULL wl_buffer, the - following wl_surface.commit will remove the surface content. + If wl_surface.attach is sent with a NULL wl_buffer, the + following wl_surface.commit will remove the surface content. - If a pending wl_buffer has been destroyed, the result is not specified. - Many compositors are known to remove the surface content on the following - wl_surface.commit, but this behaviour is not universal. Clients seeking to - maximise compatibility should not destroy pending buffers and should - ensure that they explicitly remove content from surfaces, even after - destroying buffers. + If a pending wl_buffer has been destroyed, the result is not specified. + Many compositors are known to remove the surface content on the following + wl_surface.commit, but this behaviour is not universal. Clients seeking to + maximise compatibility should not destroy pending buffers and should + ensure that they explicitly remove content from surfaces, even after + destroying buffers. + summary="buffer of surface contents"/> - This request is used to describe the regions where the pending - buffer is different from the current surface contents, and where - the surface therefore needs to be repainted. The compositor - ignores the parts of the damage that fall outside of the surface. + This request is used to describe the regions where the pending + buffer is different from the current surface contents, and where + the surface therefore needs to be repainted. The compositor + ignores the parts of the damage that fall outside of the surface. - Damage is double-buffered state, see wl_surface.commit. + Damage is double-buffered state, see wl_surface.commit. - The damage rectangle is specified in surface-local coordinates, - where x and y specify the upper left corner of the damage rectangle. + The damage rectangle is specified in surface-local coordinates, + where x and y specify the upper left corner of the damage rectangle. - The initial value for pending damage is empty: no damage. - wl_surface.damage adds pending damage: the new pending damage - is the union of old pending damage and the given rectangle. + The initial value for pending damage is empty: no damage. + wl_surface.damage adds pending damage: the new pending damage + is the union of old pending damage and the given rectangle. - wl_surface.commit assigns pending damage as the current damage, - and clears pending damage. The server will clear the current - damage as it repaints the surface. + wl_surface.commit assigns pending damage as the current damage, + and clears pending damage. The server will clear the current + damage as it repaints the surface. - Note! New clients should not use this request. Instead damage can be - posted with wl_surface.damage_buffer which uses buffer coordinates - instead of surface coordinates. + Note! New clients should not use this request. Instead damage can be + posted with wl_surface.damage_buffer which uses buffer coordinates + instead of surface coordinates. @@ -1565,148 +1610,175 @@ - Request a notification when it is a good time to start drawing a new - frame, by creating a frame callback. This is useful for throttling - redrawing operations, and driving animations. + Request a notification when it is a good time to start drawing a new + frame, by creating a frame callback. This is useful for throttling + redrawing operations, and driving animations. - When a client is animating on a wl_surface, it can use the 'frame' - request to get notified when it is a good time to draw and commit the - next frame of animation. If the client commits an update earlier than - that, it is likely that some updates will not make it to the display, - and the client is wasting resources by drawing too often. + When a client is animating on a wl_surface, it can use the 'frame' + request to get notified when it is a good time to draw and commit the + next frame of animation. If the client commits an update earlier than + that, it is likely that some updates will not make it to the display, + and the client is wasting resources by drawing too often. - The frame request will take effect on the next wl_surface.commit. - The notification will only be posted for one frame unless - requested again. For a wl_surface, the notifications are posted in - the order the frame requests were committed. + The frame request will take effect on the next wl_surface.commit. + The notification will only be posted for one frame unless + requested again. For a wl_surface, the notifications are posted in + the order the frame requests were committed. - The server must send the notifications so that a client - will not send excessive updates, while still allowing - the highest possible update rate for clients that wait for the reply - before drawing again. The server should give some time for the client - to draw and commit after sending the frame callback events to let it - hit the next output refresh. + The server must send the notifications so that a client + will not send excessive updates, while still allowing + the highest possible update rate for clients that wait for the reply + before drawing again. The server should give some time for the client + to draw and commit after sending the frame callback events to let it + hit the next output refresh. - A server should avoid signaling the frame callbacks if the - surface is not visible in any way, e.g. the surface is off-screen, - or completely obscured by other opaque surfaces. + A server should avoid signaling the frame callbacks if the + surface is not visible in any way, e.g. the surface is off-screen, + or completely obscured by other opaque surfaces. - The object returned by this request will be destroyed by the - compositor after the callback is fired and as such the client must not - attempt to use it after that point. + The object returned by this request will be destroyed by the + compositor after the callback is fired and as such the client must not + attempt to use it after that point. - The callback_data passed in the callback is the current time, in - milliseconds, with an undefined base. + The callback_data passed in the callback is the current time, in + milliseconds, with an undefined base. - This request sets the region of the surface that contains - opaque content. + This request sets the region of the surface that contains + opaque content. - The opaque region is an optimization hint for the compositor - that lets it optimize the redrawing of content behind opaque - regions. Setting an opaque region is not required for correct - behaviour, but marking transparent content as opaque will result - in repaint artifacts. + The opaque region is an optimization hint for the compositor + that lets it optimize the redrawing of content behind opaque + regions. Setting an opaque region is not required for correct + behaviour, but marking transparent content as opaque will result + in repaint artifacts. - The opaque region is specified in surface-local coordinates. + The opaque region is specified in surface-local coordinates. - The compositor ignores the parts of the opaque region that fall - outside of the surface. + The compositor ignores the parts of the opaque region that fall + outside of the surface. - Opaque region is double-buffered state, see wl_surface.commit. + Opaque region is double-buffered state, see wl_surface.commit. - wl_surface.set_opaque_region changes the pending opaque region. - wl_surface.commit copies the pending region to the current region. - Otherwise, the pending and current regions are never changed. + wl_surface.set_opaque_region changes the pending opaque region. + wl_surface.commit copies the pending region to the current region. + Otherwise, the pending and current regions are never changed. - The initial value for an opaque region is empty. Setting the pending - opaque region has copy semantics, and the wl_region object can be - destroyed immediately. A NULL wl_region causes the pending opaque - region to be set to empty. + The initial value for an opaque region is empty. Setting the pending + opaque region has copy semantics, and the wl_region object can be + destroyed immediately. A NULL wl_region causes the pending opaque + region to be set to empty. + summary="opaque region of the surface"/> - This request sets the region of the surface that can receive - pointer and touch events. + This request sets the region of the surface that can receive + pointer and touch events. - Input events happening outside of this region will try the next - surface in the server surface stack. The compositor ignores the - parts of the input region that fall outside of the surface. + Input events happening outside of this region will try the next + surface in the server surface stack. The compositor ignores the + parts of the input region that fall outside of the surface. - The input region is specified in surface-local coordinates. + The input region is specified in surface-local coordinates. - Input region is double-buffered state, see wl_surface.commit. + Input region is double-buffered state, see wl_surface.commit. - wl_surface.set_input_region changes the pending input region. - wl_surface.commit copies the pending region to the current region. - Otherwise the pending and current regions are never changed, - except cursor and icon surfaces are special cases, see - wl_pointer.set_cursor and wl_data_device.start_drag. + wl_surface.set_input_region changes the pending input region. + wl_surface.commit copies the pending region to the current region. + Otherwise the pending and current regions are never changed, + except cursor and icon surfaces are special cases, see + wl_pointer.set_cursor and wl_data_device.start_drag. - The initial value for an input region is infinite. That means the - whole surface will accept input. Setting the pending input region - has copy semantics, and the wl_region object can be destroyed - immediately. A NULL wl_region causes the input region to be set - to infinite. + The initial value for an input region is infinite. That means the + whole surface will accept input. Setting the pending input region + has copy semantics, and the wl_region object can be destroyed + immediately. A NULL wl_region causes the input region to be set + to infinite. + summary="input region of the surface"/> - Surface state (input, opaque, and damage regions, attached buffers, - etc.) is double-buffered. Protocol requests modify the pending state, - as opposed to the active state in use by the compositor. + Surface state (input, opaque, and damage regions, attached buffers, + etc.) is double-buffered. Protocol requests modify the pending state, + as opposed to the active state in use by the compositor. - A commit request atomically creates a content update from the pending - state, even if the pending state has not been touched. The content - update is placed in a queue until it becomes active. After commit, the - new pending state is as documented for each related request. + All requests that need a commit to become effective are documented + to affect double-buffered state. - When the content update is applied, the wl_buffer is applied before all - other state. This means that all coordinates in double-buffered state - are relative to the newly attached wl_buffers, except for - wl_surface.attach itself. If there is no newly attached wl_buffer, the - coordinates are relative to the previous content update. + Other interfaces may add further double-buffered surface state. - All requests that need a commit to become effective are documented - to affect double-buffered state. + A commit request atomically creates a Content Update (CU) from the + pending state, even if the pending state has not been touched. The + content update is placed at the end of a per-surface queue until it + becomes active. After commit, the new pending state is as documented for + each related request. - Other interfaces may add further double-buffered surface state. + A CU is either a Desync Content Update (DCU) or a Sync Content Update + (SCU). If the surface is effectively synchronized at the commit request, + it is a SCU, otherwise a DCU. + + When a surface transitions from effectively synchronized to effectively + desynchronized, all SCUs in its queue which are not reachable by any + DCU become DCUs and dependency edges from outside the queue to these CUs + are removed. + + See wl_subsurface for the definition of 'effectively synchronized' and + 'effectively desynchronized'. + + When a CU is placed in the queue, the CU has a dependency on the CU in + front of it and to the SCU at end of the queue of every direct child + surface if that SCU exists and does not have another dependent. This can + form a directed acyclic graph of CUs with dependencies as edges. + + In addition to surface state, the CU can have constraints that must be + satisfied before it can be applied. Other interfaces may add CU + constraints. + + All DCUs which do not have a SCU in front of themselves in their queue, + are candidates. If the graph that's reachable by a candidate does not + have any unsatisfied constraints, the entire graph must be applied + atomically. + + When a CU is applied, the wl_buffer is applied before all other state. + This means that all coordinates in double-buffered state are relative to + the newly attached wl_buffers, except for wl_surface.attach itself. If + there is no newly attached wl_buffer, the coordinates are relative to + the previous content update. - This is emitted whenever a surface's creation, movement, or resizing - results in some part of it being within the scanout region of an - output. + This is emitted whenever a surface's creation, movement, or resizing + results in some part of it being within the scanout region of an + output. - Note that a surface may be overlapping with zero or more outputs. + Note that a surface may be overlapping with zero or more outputs. - This is emitted whenever a surface's creation, movement, or resizing - results in it no longer having any part of it within the scanout region - of an output. + This is emitted whenever a surface's creation, movement, or resizing + results in it no longer having any part of it within the scanout region + of an output. - Clients should not use the number of outputs the surface is on for frame - throttling purposes. The surface might be hidden even if no leave event - has been sent, and the compositor might expect new surface content - updates even if no enter event has been sent. The frame event should be - used instead. + Clients should not use the number of outputs the surface is on for frame + throttling purposes. The surface might be hidden even if no leave event + has been sent, and the compositor might expect new surface content + updates even if no enter event has been sent. The frame event should be + used instead. @@ -1715,109 +1787,109 @@ - This request sets the transformation that the client has already applied - to the content of the buffer. The accepted values for the transform - parameter are the values for wl_output.transform. + This request sets the transformation that the client has already applied + to the content of the buffer. The accepted values for the transform + parameter are the values for wl_output.transform. - The compositor applies the inverse of this transformation whenever it - uses the buffer contents. + The compositor applies the inverse of this transformation whenever it + uses the buffer contents. - Buffer transform is double-buffered state, see wl_surface.commit. + Buffer transform is double-buffered state, see wl_surface.commit. - A newly created surface has its buffer transformation set to normal. + A newly created surface has its buffer transformation set to normal. - wl_surface.set_buffer_transform changes the pending buffer - transformation. wl_surface.commit copies the pending buffer - transformation to the current one. Otherwise, the pending and current - values are never changed. + wl_surface.set_buffer_transform changes the pending buffer + transformation. wl_surface.commit copies the pending buffer + transformation to the current one. Otherwise, the pending and current + values are never changed. - The purpose of this request is to allow clients to render content - according to the output transform, thus permitting the compositor to - use certain optimizations even if the display is rotated. Using - hardware overlays and scanning out a client buffer for fullscreen - surfaces are examples of such optimizations. Those optimizations are - highly dependent on the compositor implementation, so the use of this - request should be considered on a case-by-case basis. + The purpose of this request is to allow clients to render content + according to the output transform, thus permitting the compositor to + use certain optimizations even if the display is rotated. Using + hardware overlays and scanning out a client buffer for fullscreen + surfaces are examples of such optimizations. Those optimizations are + highly dependent on the compositor implementation, so the use of this + request should be considered on a case-by-case basis. - Note that if the transform value includes 90 or 270 degree rotation, - the width of the buffer will become the surface height and the height - of the buffer will become the surface width. + Note that if the transform value includes 90 or 270 degree rotation, + the width of the buffer will become the surface height and the height + of the buffer will become the surface width. - If transform is not one of the values from the - wl_output.transform enum the invalid_transform protocol error - is raised. + If transform is not one of the values from the + wl_output.transform enum the invalid_transform protocol error + is raised. + summary="transform for interpreting buffer contents"/> - This request sets an optional scaling factor on how the compositor - interprets the contents of the buffer attached to the window. + This request sets an optional scaling factor on how the compositor + interprets the contents of the buffer attached to the window. - Buffer scale is double-buffered state, see wl_surface.commit. + Buffer scale is double-buffered state, see wl_surface.commit. - A newly created surface has its buffer scale set to 1. + A newly created surface has its buffer scale set to 1. - wl_surface.set_buffer_scale changes the pending buffer scale. - wl_surface.commit copies the pending buffer scale to the current one. - Otherwise, the pending and current values are never changed. + wl_surface.set_buffer_scale changes the pending buffer scale. + wl_surface.commit copies the pending buffer scale to the current one. + Otherwise, the pending and current values are never changed. - The purpose of this request is to allow clients to supply higher - resolution buffer data for use on high resolution outputs. It is - intended that you pick the same buffer scale as the scale of the - output that the surface is displayed on. This means the compositor - can avoid scaling when rendering the surface on that output. + The purpose of this request is to allow clients to supply higher + resolution buffer data for use on high resolution outputs. It is + intended that you pick the same buffer scale as the scale of the + output that the surface is displayed on. This means the compositor + can avoid scaling when rendering the surface on that output. - Note that if the scale is larger than 1, then you have to attach - a buffer that is larger (by a factor of scale in each dimension) - than the desired surface size. + Note that if the scale is larger than 1, then you have to attach + a buffer that is larger (by a factor of scale in each dimension) + than the desired surface size. - If scale is not greater than 0 the invalid_scale protocol error is - raised. + If scale is not greater than 0 the invalid_scale protocol error is + raised. + summary="scale for interpreting buffer contents"/> - This request is used to describe the regions where the pending - buffer is different from the current surface contents, and where - the surface therefore needs to be repainted. The compositor - ignores the parts of the damage that fall outside of the surface. + This request is used to describe the regions where the pending + buffer is different from the current surface contents, and where + the surface therefore needs to be repainted. The compositor + ignores the parts of the damage that fall outside of the surface. - Damage is double-buffered state, see wl_surface.commit. + Damage is double-buffered state, see wl_surface.commit. - The damage rectangle is specified in buffer coordinates, - where x and y specify the upper left corner of the damage rectangle. + The damage rectangle is specified in buffer coordinates, + where x and y specify the upper left corner of the damage rectangle. - The initial value for pending damage is empty: no damage. - wl_surface.damage_buffer adds pending damage: the new pending - damage is the union of old pending damage and the given rectangle. + The initial value for pending damage is empty: no damage. + wl_surface.damage_buffer adds pending damage: the new pending + damage is the union of old pending damage and the given rectangle. - wl_surface.commit assigns pending damage as the current damage, - and clears pending damage. The server will clear the current - damage as it repaints the surface. + wl_surface.commit assigns pending damage as the current damage, + and clears pending damage. The server will clear the current + damage as it repaints the surface. - This request differs from wl_surface.damage in only one way - it - takes damage in buffer coordinates instead of surface-local - coordinates. While this generally is more intuitive than surface - coordinates, it is especially desirable when using wp_viewport - or when a drawing library (like EGL) is unaware of buffer scale - and buffer transform. + This request differs from wl_surface.damage in only one way - it + takes damage in buffer coordinates instead of surface-local + coordinates. While this generally is more intuitive than surface + coordinates, it is especially desirable when using wp_viewport + or when a drawing library (like EGL) is unaware of buffer scale + and buffer transform. - Note: Because buffer transformation changes and damage requests may - be interleaved in the protocol stream, it is impossible to determine - the actual mapping between surface and buffer damage until - wl_surface.commit time. Therefore, compositors wishing to take both - kinds of damage into account will have to accumulate damage from the - two requests separately and only transform from one to the other - after receiving the wl_surface.commit. + Note: Because buffer transformation changes and damage requests may + be interleaved in the protocol stream, it is impossible to determine + the actual mapping between surface and buffer damage until + wl_surface.commit time. Therefore, compositors wishing to take both + kinds of damage into account will have to accumulate damage from the + two requests separately and only transform from one to the other + after receiving the wl_surface.commit. @@ -1829,21 +1901,21 @@ - The x and y arguments specify the location of the new pending - buffer's upper left corner, relative to the current buffer's upper - left corner, in surface-local coordinates. In other words, the - x and y, combined with the new surface size define in which - directions the surface's size changes. + The x and y arguments specify the location of the new pending + buffer's upper left corner, relative to the current buffer's upper + left corner, in surface-local coordinates. In other words, the + x and y, combined with the new surface size define in which + directions the surface's size changes. - The exact semantics of wl_surface.offset are role-specific. Refer to - the documentation of specific roles for more information. + The exact semantics of wl_surface.offset are role-specific. Refer to + the documentation of specific roles for more information. - Surface location offset is double-buffered state, see - wl_surface.commit. + Surface location offset is double-buffered state, see + wl_surface.commit. - This request is semantically equivalent to and the replaces the x and y - arguments in the wl_surface.attach request in wl_surface versions prior - to 5. See wl_surface.attach for details. + This request is semantically equivalent to and the replaces the x and y + arguments in the wl_surface.attach request in wl_surface versions prior + to 5. See wl_surface.attach for details. @@ -1853,37 +1925,63 @@ - This event indicates the preferred buffer scale for this surface. It is - sent whenever the compositor's preference changes. + This event indicates the preferred buffer scale for this surface. It is + sent whenever the compositor's preference changes. - Before receiving this event the preferred buffer scale for this surface - is 1. + Before receiving this event the preferred buffer scale for this surface + is 1. - It is intended that scaling aware clients use this event to scale their - content and use wl_surface.set_buffer_scale to indicate the scale they - have rendered with. This allows clients to supply a higher detail - buffer. + It is intended that scaling aware clients use this event to scale their + content and use wl_surface.set_buffer_scale to indicate the scale they + have rendered with. This allows clients to supply a higher detail + buffer. - The compositor shall emit a scale value greater than 0. + The compositor shall emit a scale value greater than 0. - This event indicates the preferred buffer transform for this surface. - It is sent whenever the compositor's preference changes. + This event indicates the preferred buffer transform for this surface. + It is sent whenever the compositor's preference changes. - Before receiving this event the preferred buffer transform for this - surface is normal. + Before receiving this event the preferred buffer transform for this + surface is normal. - Applying this transformation to the surface buffer contents and using - wl_surface.set_buffer_transform might allow the compositor to use the - surface buffer more efficiently. + Applying this transformation to the surface buffer contents and using + wl_surface.set_buffer_transform might allow the compositor to use the + surface buffer more efficiently. + summary="preferred transform"/> + + + + + + Create a callback for the release of the buffer attached by the client + with wl_surface.attach. + + The compositor will release the buffer when it has finished its usage of + the underlying storage for the relevant commit. Once the client receives + this event, and assuming the associated buffer is not pending release + from other wl_surface.commit requests, the client can safely re-use the + buffer. + + Release callbacks are double-buffered state, and will be associated + with the pending buffer at wl_surface.commit time. + + The callback_data passed in the wl_callback.done event is unused and + is always zero. + + Sending this request without attaching a non-null buffer in the same + content update is a protocol error. The compositor will send the + no_buffer error in this case. + + + @@ -1896,8 +1994,8 @@ - This is a bitmask of capabilities this seat has; if a member is - set, then it is present on the seat. + This is a bitmask of capabilities this seat has; if a member is + set, then it is present on the seat. @@ -1906,81 +2004,81 @@ - These errors can be emitted in response to wl_seat requests. + These errors can be emitted in response to wl_seat requests. + summary="get_pointer, get_keyboard or get_touch called on seat without the matching capability"/> - This is sent on binding to the seat global or whenever a seat gains - or loses the pointer, keyboard or touch capabilities. - The argument is a capability enum containing the complete set of - capabilities this seat has. + This is sent on binding to the seat global or whenever a seat gains + or loses the pointer, keyboard or touch capabilities. + The argument is a capability enum containing the complete set of + capabilities this seat has. - When the pointer capability is added, a client may create a - wl_pointer object using the wl_seat.get_pointer request. This object - will receive pointer events until the capability is removed in the - future. + When the pointer capability is added, a client may create a + wl_pointer object using the wl_seat.get_pointer request. This object + will receive pointer events until the capability is removed in the + future. - When the pointer capability is removed, a client should destroy the - wl_pointer objects associated with the seat where the capability was - removed, using the wl_pointer.release request. No further pointer - events will be received on these objects. + When the pointer capability is removed, a client should destroy the + wl_pointer objects associated with the seat where the capability was + removed, using the wl_pointer.release request. No further pointer + events will be received on these objects. - In some compositors, if a seat regains the pointer capability and a - client has a previously obtained wl_pointer object of version 4 or - less, that object may start sending pointer events again. This - behavior is considered a misinterpretation of the intended behavior - and must not be relied upon by the client. wl_pointer objects of - version 5 or later must not send events if created before the most - recent event notifying the client of an added pointer capability. + In some compositors, if a seat regains the pointer capability and a + client has a previously obtained wl_pointer object of version 4 or + less, that object may start sending pointer events again. This + behavior is considered a misinterpretation of the intended behavior + and must not be relied upon by the client. wl_pointer objects of + version 5 or later must not send events if created before the most + recent event notifying the client of an added pointer capability. - The above behavior also applies to wl_keyboard and wl_touch with the - keyboard and touch capabilities, respectively. + The above behavior also applies to wl_keyboard and wl_touch with the + keyboard and touch capabilities, respectively. - The ID provided will be initialized to the wl_pointer interface - for this seat. + The ID provided will be initialized to the wl_pointer interface + for this seat. - This request only takes effect if the seat has the pointer - capability, or has had the pointer capability in the past. - It is a protocol violation to issue this request on a seat that has - never had the pointer capability. The missing_capability error will - be sent in this case. + This request only takes effect if the seat has the pointer + capability, or has had the pointer capability in the past. + It is a protocol violation to issue this request on a seat that has + never had the pointer capability. The missing_capability error will + be sent in this case. - The ID provided will be initialized to the wl_keyboard interface - for this seat. + The ID provided will be initialized to the wl_keyboard interface + for this seat. - This request only takes effect if the seat has the keyboard - capability, or has had the keyboard capability in the past. - It is a protocol violation to issue this request on a seat that has - never had the keyboard capability. The missing_capability error will - be sent in this case. + This request only takes effect if the seat has the keyboard + capability, or has had the keyboard capability in the past. + It is a protocol violation to issue this request on a seat that has + never had the keyboard capability. The missing_capability error will + be sent in this case. - The ID provided will be initialized to the wl_touch interface - for this seat. + The ID provided will be initialized to the wl_touch interface + for this seat. - This request only takes effect if the seat has the touch - capability, or has had the touch capability in the past. - It is a protocol violation to issue this request on a seat that has - never had the touch capability. The missing_capability error will - be sent in this case. + This request only takes effect if the seat has the touch + capability, or has had the touch capability in the past. + It is a protocol violation to issue this request on a seat that has + never had the touch capability. The missing_capability error will + be sent in this case. @@ -1989,22 +2087,22 @@ - In a multi-seat configuration the seat name can be used by clients to - help identify which physical devices the seat represents. + In a multi-seat configuration the seat name can be used by clients to + help identify which physical devices the seat represents. - The seat name is a UTF-8 string with no convention defined for its - contents. Each name is unique among all wl_seat globals. The name is - only guaranteed to be unique for the current compositor instance. + The seat name is a UTF-8 string with no convention defined for its + contents. Each name is unique among all wl_seat globals. The name is + only guaranteed to be unique for the current compositor instance. - The same seat names are used for all clients. Thus, the name can be - shared across processes to refer to a specific wl_seat global. + The same seat names are used for all clients. Thus, the name can be + shared across processes to refer to a specific wl_seat global. - The name event is sent after binding to the seat global, and should be sent - before announcing capabilities. This event only sent once per seat object, - and the name does not change over the lifetime of the wl_seat global. + The name event is sent after binding to the seat global, and should be sent + before announcing capabilities. This event only sent once per seat object, + and the name does not change over the lifetime of the wl_seat global. - Compositors may re-use the same seat name if the wl_seat global is - destroyed and re-created later. + Compositors may re-use the same seat name if the wl_seat global is + destroyed and re-created later. @@ -2013,8 +2111,8 @@ - Using this request a client can tell the server that it is not going to - use the seat object anymore. + Using this request a client can tell the server that it is not going to + use the seat object anymore. @@ -2038,55 +2136,55 @@ - Set the pointer surface, i.e., the surface that contains the - pointer image (cursor). This request gives the surface the role - of a cursor. If the surface already has another role, it raises - a protocol error. + Set the pointer surface, i.e., the surface that contains the + pointer image (cursor). This request gives the surface the role + of a cursor. If the surface already has another role, it raises + a protocol error. - The cursor actually changes only if the pointer - focus for this device is one of the requesting client's surfaces - or the surface parameter is the current pointer surface. If - there was a previous surface set with this request it is - replaced. If surface is NULL, the pointer image is hidden. + The cursor actually changes only if the pointer + focus for this device is one of the requesting client's surfaces + or the surface parameter is the current pointer surface. If + there was a previous surface set with this request it is + replaced. If surface is NULL, the pointer image is hidden. - The parameters hotspot_x and hotspot_y define the position of - the pointer surface relative to the pointer location. Its - top-left corner is always at (x, y) - (hotspot_x, hotspot_y), - where (x, y) are the coordinates of the pointer location, in - surface-local coordinates. + The parameters hotspot_x and hotspot_y define the position of + the pointer surface relative to the pointer location. Its + top-left corner is always at (x, y) - (hotspot_x, hotspot_y), + where (x, y) are the coordinates of the pointer location, in + surface-local coordinates. - On wl_surface.offset requests to the pointer surface, hotspot_x - and hotspot_y are decremented by the x and y parameters - passed to the request. The offset must be applied by - wl_surface.commit as usual. + On wl_surface.offset requests to the pointer surface, hotspot_x + and hotspot_y are decremented by the x and y parameters + passed to the request. The offset must be applied by + wl_surface.commit as usual. - The hotspot can also be updated by passing the currently set - pointer surface to this request with new values for hotspot_x - and hotspot_y. + The hotspot can also be updated by passing the currently set + pointer surface to this request with new values for hotspot_x + and hotspot_y. - The input region is ignored for wl_surfaces with the role of - a cursor. When the use as a cursor ends, the wl_surface is - unmapped. + The input region is ignored for wl_surfaces with the role of + a cursor. When the use as a cursor ends, the wl_surface is + unmapped. - The serial parameter must match the latest wl_pointer.enter - serial number sent to the client. Otherwise the request will be - ignored. + The serial parameter must match the latest wl_pointer.enter + serial number sent to the client. Otherwise the request will be + ignored. + summary="pointer surface"/> - Notification that this seat's pointer is focused on a certain - surface. + Notification that this seat's pointer is focused on a certain + surface. - When a seat's focus enters a surface, the pointer image - is undefined and a client should respond to this event by setting - an appropriate pointer image with the set_cursor request. + When a seat's focus enters a surface, the pointer image + is undefined and a client should respond to this event by setting + an appropriate pointer image with the set_cursor request. @@ -2096,11 +2194,11 @@ - Notification that this seat's pointer is no longer focused on - a certain surface. + Notification that this seat's pointer is no longer focused on + a certain surface. - The leave notification is sent before the enter notification - for the new focus. + The leave notification is sent before the enter notification + for the new focus. @@ -2108,9 +2206,9 @@ - Notification of pointer location change. The arguments - surface_x and surface_y are the location relative to the - focused surface. + Notification of pointer location change. The arguments + surface_x and surface_y are the location relative to the + focused surface. @@ -2119,8 +2217,8 @@ - Describes the physical state of a button that produced the button - event. + Describes the physical state of a button that produced the button + event. @@ -2128,20 +2226,20 @@ - Mouse button click and release notifications. + Mouse button click and release notifications. - The location of the click is given by the last motion or - enter event. - The time argument is a timestamp with millisecond - granularity, with an undefined base. + The location of the click is given by the last motion or + enter event. + The time argument is a timestamp with millisecond + granularity, with an undefined base. - The button is a button code as defined in the Linux kernel's - linux/input-event-codes.h header file, e.g. BTN_LEFT. + The button is a button code as defined in the Linux kernel's + linux/input-event-codes.h header file, e.g. BTN_LEFT. - Any 16-bit button code value is reserved for future additions to the - kernel's event code list. All other button codes above 0xFFFF are - currently undefined but may be used in future versions of this - protocol. + Any 16-bit button code value is reserved for future additions to the + kernel's event code list. All other button codes above 0xFFFF are + currently undefined but may be used in future versions of this + protocol. @@ -2151,7 +2249,7 @@ - Describes the axis types of scroll events. + Describes the axis types of scroll events. @@ -2159,22 +2257,22 @@ - Scroll and other axis notifications. + Scroll and other axis notifications. - For scroll events (vertical and horizontal scroll axes), the - value parameter is the length of a vector along the specified - axis in a coordinate space identical to those of motion events, - representing a relative movement along the specified axis. + For scroll events (vertical and horizontal scroll axes), the + value parameter is the length of a vector along the specified + axis in a coordinate space identical to those of motion events, + representing a relative movement along the specified axis. - For devices that support movements non-parallel to axes multiple - axis events will be emitted. + For devices that support movements non-parallel to axes multiple + axis events will be emitted. - When applicable, for example for touch pads, the server can - choose to emit scroll events where the motion vector is - equivalent to a motion event vector. + When applicable, for example for touch pads, the server can + choose to emit scroll events where the motion vector is + equivalent to a motion event vector. - When applicable, a client can transform its content relative to the - scroll distance. + When applicable, a client can transform its content relative to the + scroll distance. @@ -2185,11 +2283,11 @@ - Using this request a client can tell the server that it is not going to - use the pointer object anymore. + Using this request a client can tell the server that it is not going to + use the pointer object anymore. - This request destroys the pointer proxy object, so clients must not call - wl_pointer_destroy() after using this request. + This request destroys the pointer proxy object, so clients must not call + wl_pointer_destroy() after using this request. @@ -2197,61 +2295,61 @@ - Indicates the end of a set of events that logically belong together. - A client is expected to accumulate the data in all events within the - frame before proceeding. + Indicates the end of a set of events that logically belong together. + A client is expected to accumulate the data in all events within the + frame before proceeding. - All wl_pointer events before a wl_pointer.frame event belong - logically together. For example, in a diagonal scroll motion the - compositor will send an optional wl_pointer.axis_source event, two - wl_pointer.axis events (horizontal and vertical) and finally a - wl_pointer.frame event. The client may use this information to - calculate a diagonal vector for scrolling. + All wl_pointer events before a wl_pointer.frame event belong + logically together. For example, in a diagonal scroll motion the + compositor will send an optional wl_pointer.axis_source event, two + wl_pointer.axis events (horizontal and vertical) and finally a + wl_pointer.frame event. The client may use this information to + calculate a diagonal vector for scrolling. - When multiple wl_pointer.axis events occur within the same frame, - the motion vector is the combined motion of all events. - When a wl_pointer.axis and a wl_pointer.axis_stop event occur within - the same frame, this indicates that axis movement in one axis has - stopped but continues in the other axis. - When multiple wl_pointer.axis_stop events occur within the same - frame, this indicates that these axes stopped in the same instance. + When multiple wl_pointer.axis events occur within the same frame, + the motion vector is the combined motion of all events. + When a wl_pointer.axis and a wl_pointer.axis_stop event occur within + the same frame, this indicates that axis movement in one axis has + stopped but continues in the other axis. + When multiple wl_pointer.axis_stop events occur within the same + frame, this indicates that these axes stopped in the same instance. - A wl_pointer.frame event is sent for every logical event group, - even if the group only contains a single wl_pointer event. - Specifically, a client may get a sequence: motion, frame, button, - frame, axis, frame, axis_stop, frame. + A wl_pointer.frame event is sent for every logical event group, + even if the group only contains a single wl_pointer event. + Specifically, a client may get a sequence: motion, frame, button, + frame, axis, frame, axis_stop, frame. - The wl_pointer.enter and wl_pointer.leave events are logical events - generated by the compositor and not the hardware. These events are - also grouped by a wl_pointer.frame. When a pointer moves from one - surface to another, a compositor should group the - wl_pointer.leave event within the same wl_pointer.frame. - However, a client must not rely on wl_pointer.leave and - wl_pointer.enter being in the same wl_pointer.frame. - Compositor-specific policies may require the wl_pointer.leave and - wl_pointer.enter event being split across multiple wl_pointer.frame - groups. + The wl_pointer.enter and wl_pointer.leave events are logical events + generated by the compositor and not the hardware. These events are + also grouped by a wl_pointer.frame. When a pointer moves from one + surface to another, a compositor should group the + wl_pointer.leave event within the same wl_pointer.frame. + However, a client must not rely on wl_pointer.leave and + wl_pointer.enter being in the same wl_pointer.frame. + Compositor-specific policies may require the wl_pointer.leave and + wl_pointer.enter event being split across multiple wl_pointer.frame + groups. - Describes the source types for axis events. This indicates to the - client how an axis event was physically generated; a client may - adjust the user interface accordingly. For example, scroll events - from a "finger" source may be in a smooth coordinate space with - kinetic scrolling whereas a "wheel" source may be in discrete steps - of a number of lines. + Describes the source types for axis events. This indicates to the + client how an axis event was physically generated; a client may + adjust the user interface accordingly. For example, scroll events + from a "finger" source may be in a smooth coordinate space with + kinetic scrolling whereas a "wheel" source may be in discrete steps + of a number of lines. - The "continuous" axis source is a device generating events in a - continuous coordinate space, but using something other than a - finger. One example for this source is button-based scrolling where - the vertical motion of a device is converted to scroll events while - a button is held down. + The "continuous" axis source is a device generating events in a + continuous coordinate space, but using something other than a + finger. One example for this source is button-based scrolling where + the vertical motion of a device is converted to scroll events while + a button is held down. - The "wheel tilt" axis source indicates that the actual device is a - wheel but the scroll event is not caused by a rotation but a - (usually sideways) tilt of the wheel. + The "wheel tilt" axis source indicates that the actual device is a + wheel but the scroll event is not caused by a rotation but a + (usually sideways) tilt of the wheel. @@ -2261,51 +2359,51 @@ - Source information for scroll and other axes. + Source information for scroll and other axes. - This event does not occur on its own. It is sent before a - wl_pointer.frame event and carries the source information for - all events within that frame. + This event does not occur on its own. It is sent before a + wl_pointer.frame event and carries the source information for + all events within that frame. - The source specifies how this event was generated. If the source is - wl_pointer.axis_source.finger, a wl_pointer.axis_stop event will be - sent when the user lifts the finger off the device. + The source specifies how this event was generated. If the source is + wl_pointer.axis_source.finger, a wl_pointer.axis_stop event will be + sent when the user lifts the finger off the device. - If the source is wl_pointer.axis_source.wheel, - wl_pointer.axis_source.wheel_tilt or - wl_pointer.axis_source.continuous, a wl_pointer.axis_stop event may - or may not be sent. Whether a compositor sends an axis_stop event - for these sources is hardware-specific and implementation-dependent; - clients must not rely on receiving an axis_stop event for these - scroll sources and should treat scroll sequences from these scroll - sources as unterminated by default. + If the source is wl_pointer.axis_source.wheel, + wl_pointer.axis_source.wheel_tilt or + wl_pointer.axis_source.continuous, a wl_pointer.axis_stop event may + or may not be sent. Whether a compositor sends an axis_stop event + for these sources is hardware-specific and implementation-dependent; + clients must not rely on receiving an axis_stop event for these + scroll sources and should treat scroll sequences from these scroll + sources as unterminated by default. - This event is optional. If the source is unknown for a particular - axis event sequence, no event is sent. - Only one wl_pointer.axis_source event is permitted per frame. + This event is optional. If the source is unknown for a particular + axis event sequence, no event is sent. + Only one wl_pointer.axis_source event is permitted per frame. - The order of wl_pointer.axis_discrete and wl_pointer.axis_source is - not guaranteed. + The order of wl_pointer.axis_discrete and wl_pointer.axis_source is + not guaranteed. - Stop notification for scroll and other axes. + Stop notification for scroll and other axes. - For some wl_pointer.axis_source types, a wl_pointer.axis_stop event - is sent to notify a client that the axis sequence has terminated. - This enables the client to implement kinetic scrolling. - See the wl_pointer.axis_source documentation for information on when - this event may be generated. + For some wl_pointer.axis_source types, a wl_pointer.axis_stop event + is sent to notify a client that the axis sequence has terminated. + This enables the client to implement kinetic scrolling. + See the wl_pointer.axis_source documentation for information on when + this event may be generated. - Any wl_pointer.axis events with the same axis_source after this - event should be considered as the start of a new axis motion. + Any wl_pointer.axis events with the same axis_source after this + event should be considered as the start of a new axis motion. - The timestamp is to be interpreted identical to the timestamp in the - wl_pointer.axis event. The timestamp value may be the same as a - preceding wl_pointer.axis event. + The timestamp is to be interpreted identical to the timestamp in the + wl_pointer.axis event. The timestamp value may be the same as a + preceding wl_pointer.axis event. @@ -2313,36 +2411,36 @@ - Discrete step information for scroll and other axes. + Discrete step information for scroll and other axes. - This event carries the axis value of the wl_pointer.axis event in - discrete steps (e.g. mouse wheel clicks). + This event carries the axis value of the wl_pointer.axis event in + discrete steps (e.g. mouse wheel clicks). - This event is deprecated with wl_pointer version 8 - this event is not - sent to clients supporting version 8 or later. + This event is deprecated with wl_pointer version 8 - this event is not + sent to clients supporting version 8 or later. - This event does not occur on its own, it is coupled with a - wl_pointer.axis event that represents this axis value on a - continuous scale. The protocol guarantees that each axis_discrete - event is always followed by exactly one axis event with the same - axis number within the same wl_pointer.frame. Note that the protocol - allows for other events to occur between the axis_discrete and - its coupled axis event, including other axis_discrete or axis - events. A wl_pointer.frame must not contain more than one axis_discrete - event per axis type. + This event does not occur on its own, it is coupled with a + wl_pointer.axis event that represents this axis value on a + continuous scale. The protocol guarantees that each axis_discrete + event is always followed by exactly one axis event with the same + axis number within the same wl_pointer.frame. Note that the protocol + allows for other events to occur between the axis_discrete and + its coupled axis event, including other axis_discrete or axis + events. A wl_pointer.frame must not contain more than one axis_discrete + event per axis type. - This event is optional; continuous scrolling devices - like two-finger scrolling on touchpads do not have discrete - steps and do not generate this event. + This event is optional; continuous scrolling devices + like two-finger scrolling on touchpads do not have discrete + steps and do not generate this event. - The discrete value carries the directional information. e.g. a value - of -2 is two steps towards the negative direction of this axis. + The discrete value carries the directional information. e.g. a value + of -2 is two steps towards the negative direction of this axis. - The axis number is identical to the axis number in the associated - axis event. + The axis number is identical to the axis number in the associated + axis event. - The order of wl_pointer.axis_discrete and wl_pointer.axis_source is - not guaranteed. + The order of wl_pointer.axis_discrete and wl_pointer.axis_source is + not guaranteed. @@ -2350,27 +2448,27 @@ - Discrete high-resolution scroll information. + Discrete high-resolution scroll information. - This event carries high-resolution wheel scroll information, - with each multiple of 120 representing one logical scroll step - (a wheel detent). For example, an axis_value120 of 30 is one quarter of - a logical scroll step in the positive direction, a value120 of - -240 are two logical scroll steps in the negative direction within the - same hardware event. - Clients that rely on discrete scrolling should accumulate the - value120 to multiples of 120 before processing the event. + This event carries high-resolution wheel scroll information, + with each multiple of 120 representing one logical scroll step + (a wheel detent). For example, an axis_value120 of 30 is one quarter of + a logical scroll step in the positive direction, a value120 of + -240 are two logical scroll steps in the negative direction within the + same hardware event. + Clients that rely on discrete scrolling should accumulate the + value120 to multiples of 120 before processing the event. - The value120 must not be zero. + The value120 must not be zero. - This event replaces the wl_pointer.axis_discrete event in clients - supporting wl_pointer version 8 or later. + This event replaces the wl_pointer.axis_discrete event in clients + supporting wl_pointer version 8 or later. - Where a wl_pointer.axis_source event occurs in the same - wl_pointer.frame, the axis source applies to this event. + Where a wl_pointer.axis_source event occurs in the same + wl_pointer.frame, the axis source applies to this event. - The order of wl_pointer.axis_value120 and wl_pointer.axis_source is - not guaranteed. + The order of wl_pointer.axis_value120 and wl_pointer.axis_source is + not guaranteed. @@ -2380,56 +2478,56 @@ - This specifies the direction of the physical motion that caused a - wl_pointer.axis event, relative to the wl_pointer.axis direction. + This specifies the direction of the physical motion that caused a + wl_pointer.axis event, relative to the wl_pointer.axis direction. + summary="physical motion matches axis direction"/> + summary="physical motion is the inverse of the axis direction"/> - Relative directional information of the entity causing the axis - motion. + Relative directional information of the entity causing the axis + motion. - For a wl_pointer.axis event, the wl_pointer.axis_relative_direction - event specifies the movement direction of the entity causing the - wl_pointer.axis event. For example: - - if a user's fingers on a touchpad move down and this - causes a wl_pointer.axis vertical_scroll down event, the physical - direction is 'identical' - - if a user's fingers on a touchpad move down and this causes a - wl_pointer.axis vertical_scroll up scroll up event ('natural - scrolling'), the physical direction is 'inverted'. + For a wl_pointer.axis event, the wl_pointer.axis_relative_direction + event specifies the movement direction of the entity causing the + wl_pointer.axis event. For example: + - if a user's fingers on a touchpad move down and this + causes a wl_pointer.axis vertical_scroll down event, the physical + direction is 'identical' + - if a user's fingers on a touchpad move down and this causes a + wl_pointer.axis vertical_scroll up scroll up event ('natural + scrolling'), the physical direction is 'inverted'. - A client may use this information to adjust scroll motion of - components. Specifically, enabling natural scrolling causes the - content to change direction compared to traditional scrolling. - Some widgets like volume control sliders should usually match the - physical direction regardless of whether natural scrolling is - active. This event enables clients to match the scroll direction of - a widget to the physical direction. + A client may use this information to adjust scroll motion of + components. Specifically, enabling natural scrolling causes the + content to change direction compared to traditional scrolling. + Some widgets like volume control sliders should usually match the + physical direction regardless of whether natural scrolling is + active. This event enables clients to match the scroll direction of + a widget to the physical direction. - This event does not occur on its own, it is coupled with a - wl_pointer.axis event that represents this axis value. - The protocol guarantees that each axis_relative_direction event is - always followed by exactly one axis event with the same - axis number within the same wl_pointer.frame. Note that the protocol - allows for other events to occur between the axis_relative_direction - and its coupled axis event. + This event does not occur on its own, it is coupled with a + wl_pointer.axis event that represents this axis value. + The protocol guarantees that each axis_relative_direction event is + always followed by exactly one axis event with the same + axis number within the same wl_pointer.frame. Note that the protocol + allows for other events to occur between the axis_relative_direction + and its coupled axis event. - The axis number is identical to the axis number in the associated - axis event. + The axis number is identical to the axis number in the associated + axis event. - The order of wl_pointer.axis_relative_direction, - wl_pointer.axis_discrete and wl_pointer.axis_source is not - guaranteed. + The order of wl_pointer.axis_relative_direction, + wl_pointer.axis_discrete and wl_pointer.axis_source is not + guaranteed. + summary="physical direction relative to axis motion"/> @@ -2451,23 +2549,23 @@ - This specifies the format of the keymap provided to the - client with the wl_keyboard.keymap event. + This specifies the format of the keymap provided to the + client with the wl_keyboard.keymap event. + summary="no keymap; client must understand how to interpret the raw keycode"/> + summary="libxkbcommon compatible, null-terminated string; to determine the xkb keycode, clients must add 8 to the key event keycode"/> - This event provides a file descriptor to the client which can be - memory-mapped in read-only mode to provide a keyboard mapping - description. + This event provides a file descriptor to the client which can be + memory-mapped in read-only mode to provide a keyboard mapping + description. - From version 7 onwards, the fd must be mapped with MAP_PRIVATE by - the recipient, as MAP_SHARED may fail. + From version 7 onwards, the fd must be mapped with MAP_PRIVATE by + the recipient, as MAP_SHARED may fail. @@ -2476,19 +2574,19 @@ - Notification that this seat's keyboard focus is on a certain - surface. + Notification that this seat's keyboard focus is on a certain + surface. - The compositor must send the wl_keyboard.modifiers event after this - event. + The compositor must send the wl_keyboard.modifiers event after this + event. - In the wl_keyboard logical state, this event sets the active surface to - the surface argument and the keys currently logically down to the keys - in the keys argument. The compositor must not send this event if the - wl_keyboard already had an active surface immediately before this event. + In the wl_keyboard logical state, this event sets the active surface to + the surface argument and the keys currently logically down to the keys + in the keys argument. The compositor must not send this event if the + wl_keyboard already had an active surface immediately before this event. - Clients should not use the list of pressed keys to emulate key-press - events. The order of keys in the list is unspecified. + Clients should not use the list of pressed keys to emulate key-press + events. The order of keys in the list is unspecified. @@ -2497,16 +2595,16 @@ - Notification that this seat's keyboard focus is no longer on - a certain surface. + Notification that this seat's keyboard focus is no longer on + a certain surface. - The leave notification is sent before the enter notification - for the new focus. + The leave notification is sent before the enter notification + for the new focus. - In the wl_keyboard logical state, this event resets all values to their - defaults. The compositor must not send this event if the active surface - of the wl_keyboard was not equal to the surface argument immediately - before this event. + In the wl_keyboard logical state, this event resets all values to their + defaults. The compositor must not send this event if the active surface + of the wl_keyboard was not equal to the surface argument immediately + before this event. @@ -2514,15 +2612,15 @@ - Describes the physical state of a key that produced the key event. + Describes the physical state of a key that produced the key event. - Since version 10, the key can be in a "repeated" pseudo-state which - means the same as "pressed", but is used to signal repetition in the - key event. + Since version 10, the key can be in a "repeated" pseudo-state which + means the same as "pressed", but is used to signal repetition in the + key event. - The key may only enter the repeated state after entering the pressed - state and before entering the released state. This event may be - generated multiple times while the key is down. + The key may only enter the repeated state after entering the pressed + state and before entering the released state. This event may be + generated multiple times while the key is down. @@ -2531,29 +2629,29 @@ - A key was pressed or released. - The time argument is a timestamp with millisecond - granularity, with an undefined base. + A key was pressed or released. + The time argument is a timestamp with millisecond + granularity, with an undefined base. - The key is a platform-specific key code that can be interpreted - by feeding it to the keyboard mapping (see the keymap event). + The key is a platform-specific key code that can be interpreted + by feeding it to the keyboard mapping (see the keymap event). - If this event produces a change in modifiers, then the resulting - wl_keyboard.modifiers event must be sent after this event. + If this event produces a change in modifiers, then the resulting + wl_keyboard.modifiers event must be sent after this event. - In the wl_keyboard logical state, this event adds the key to the keys - currently logically down (if the state argument is pressed) or removes - the key from the keys currently logically down (if the state argument is - released). The compositor must not send this event if the wl_keyboard - did not have an active surface immediately before this event. The - compositor must not send this event if state is pressed (resp. released) - and the key was already logically down (resp. was not logically down) - immediately before this event. + In the wl_keyboard logical state, this event adds the key to the keys + currently logically down (if the state argument is pressed) or removes + the key from the keys currently logically down (if the state argument is + released). The compositor must not send this event if the wl_keyboard + did not have an active surface immediately before this event. The + compositor must not send this event if state is pressed (resp. released) + and the key was already logically down (resp. was not logically down) + immediately before this event. - Since version 10, compositors may send key events with the "repeated" - key state when a wl_keyboard.repeat_info event with a rate argument of - 0 has been received. This allows the compositor to take over the - responsibility of key repetition. + Since version 10, compositors may send key events with the "repeated" + key state when a wl_keyboard.repeat_info event with a rate argument of + 0 has been received. This allows the compositor to take over the + responsibility of key repetition. @@ -2563,19 +2661,19 @@ - Notifies clients that the modifier and/or group state has - changed, and it should update its local state. + Notifies clients that the modifier and/or group state has + changed, and it should update its local state. - The compositor may send this event without a surface of the client - having keyboard focus, for example to tie modifier information to - pointer focus instead. If a modifier event with pressed modifiers is sent - without a prior enter event, the client can assume the modifier state is - valid until it receives the next wl_keyboard.modifiers event. In order to - reset the modifier state again, the compositor can send a - wl_keyboard.modifiers event with no pressed modifiers. + The compositor may send this event without a surface of the client + having keyboard focus, for example to tie modifier information to + pointer focus instead. If a modifier event with pressed modifiers is sent + without a prior enter event, the client can assume the modifier state is + valid until it receives the next wl_keyboard.modifiers event. In order to + reset the modifier state again, the compositor can send a + wl_keyboard.modifiers event with no pressed modifiers. - In the wl_keyboard logical state, this event updates the modifiers and - group. + In the wl_keyboard logical state, this event updates the modifiers and + group. @@ -2594,23 +2692,23 @@ - Informs the client about the keyboard's repeat rate and delay. + Informs the client about the keyboard's repeat rate and delay. - This event is sent as soon as the wl_keyboard object has been created, - and is guaranteed to be received by the client before any key press - event. + This event is sent as soon as the wl_keyboard object has been created, + and is guaranteed to be received by the client before any key press + event. - Negative values for either rate or delay are illegal. A rate of zero - will disable any repeating (regardless of the value of delay). + Negative values for either rate or delay are illegal. A rate of zero + will disable any repeating (regardless of the value of delay). - This event can be sent later on as well with a new value if necessary, - so clients should continue listening for the event past the creation - of wl_keyboard. + This event can be sent later on as well with a new value if necessary, + so clients should continue listening for the event past the creation + of wl_keyboard. + summary="the rate of repeating keys in characters per second"/> + summary="delay in milliseconds since key down until repeating starts"/> @@ -2628,10 +2726,10 @@ - A new touch point has appeared on the surface. This touch point is - assigned a unique ID. Future events from this touch point reference - this ID. The ID ceases to be valid after a touch up event and may be - reused in the future. + A new touch point has appeared on the surface. This touch point is + assigned a unique ID. Future events from this touch point reference + this ID. The ID ceases to be valid after a touch up event and may be + reused in the future. @@ -2643,9 +2741,9 @@ - The touch point has disappeared. No further events will be sent for - this touch point and the touch point's ID is released and may be - reused in a future touch down event. + The touch point has disappeared. No further events will be sent for + this touch point and the touch point's ID is released and may be + reused in a future touch down event. @@ -2654,7 +2752,7 @@ - A touch point has changed coordinates. + A touch point has changed coordinates. @@ -2664,27 +2762,27 @@ - Indicates the end of a set of events that logically belong together. - A client is expected to accumulate the data in all events within the - frame before proceeding. + Indicates the end of a set of events that logically belong together. + A client is expected to accumulate the data in all events within the + frame before proceeding. - A wl_touch.frame terminates at least one event but otherwise no - guarantee is provided about the set of events within a frame. A client - must assume that any state not updated in a frame is unchanged from the - previously known state. + A wl_touch.frame terminates at least one event but otherwise no + guarantee is provided about the set of events within a frame. A client + must assume that any state not updated in a frame is unchanged from the + previously known state. - Sent if the compositor decides the touch stream is a global - gesture. No further events are sent to the clients from that - particular gesture. Touch cancellation applies to all touch points - currently active on this client's surface. The client is - responsible for finalizing the touch points, future touch points on - this surface may reuse the touch point ID. + Sent if the compositor decides the touch stream is a global + gesture. No further events are sent to the clients from that + particular gesture. Touch cancellation applies to all touch points + currently active on this client's surface. The client is + responsible for finalizing the touch points, future touch points on + this surface may reuse the touch point ID. - No frame event is required after the cancel event. + No frame event is required after the cancel event. @@ -2698,31 +2796,31 @@ - Sent when a touchpoint has changed its shape. + Sent when a touchpoint has changed its shape. - This event does not occur on its own. It is sent before a - wl_touch.frame event and carries the new shape information for - any previously reported, or new touch points of that frame. + This event does not occur on its own. It is sent before a + wl_touch.frame event and carries the new shape information for + any previously reported, or new touch points of that frame. - Other events describing the touch point such as wl_touch.down, - wl_touch.motion or wl_touch.orientation may be sent within the - same wl_touch.frame. A client should treat these events as a single - logical touch point update. The order of wl_touch.shape, - wl_touch.orientation and wl_touch.motion is not guaranteed. - A wl_touch.down event is guaranteed to occur before the first - wl_touch.shape event for this touch ID but both events may occur within - the same wl_touch.frame. + Other events describing the touch point such as wl_touch.down, + wl_touch.motion or wl_touch.orientation may be sent within the + same wl_touch.frame. A client should treat these events as a single + logical touch point update. The order of wl_touch.shape, + wl_touch.orientation and wl_touch.motion is not guaranteed. + A wl_touch.down event is guaranteed to occur before the first + wl_touch.shape event for this touch ID but both events may occur within + the same wl_touch.frame. - A touchpoint shape is approximated by an ellipse through the major and - minor axis length. The major axis length describes the longer diameter - of the ellipse, while the minor axis length describes the shorter - diameter. Major and minor are orthogonal and both are specified in - surface-local coordinates. The center of the ellipse is always at the - touchpoint location as reported by wl_touch.down or wl_touch.move. + A touchpoint shape is approximated by an ellipse through the major and + minor axis length. The major axis length describes the longer diameter + of the ellipse, while the minor axis length describes the shorter + diameter. Major and minor are orthogonal and both are specified in + surface-local coordinates. The center of the ellipse is always at the + touchpoint location as reported by wl_touch.down or wl_touch.move. - This event is only sent by the compositor if the touch device supports - shape reports. The client has to make reasonable assumptions about the - shape if it did not receive this event. + This event is only sent by the compositor if the touch device supports + shape reports. The client has to make reasonable assumptions about the + shape if it did not receive this event. @@ -2731,29 +2829,29 @@ - Sent when a touchpoint has changed its orientation. + Sent when a touchpoint has changed its orientation. - This event does not occur on its own. It is sent before a - wl_touch.frame event and carries the new shape information for - any previously reported, or new touch points of that frame. + This event does not occur on its own. It is sent before a + wl_touch.frame event and carries the new shape information for + any previously reported, or new touch points of that frame. - Other events describing the touch point such as wl_touch.down, - wl_touch.motion or wl_touch.shape may be sent within the - same wl_touch.frame. A client should treat these events as a single - logical touch point update. The order of wl_touch.shape, - wl_touch.orientation and wl_touch.motion is not guaranteed. - A wl_touch.down event is guaranteed to occur before the first - wl_touch.orientation event for this touch ID but both events may occur - within the same wl_touch.frame. + Other events describing the touch point such as wl_touch.down, + wl_touch.motion or wl_touch.shape may be sent within the + same wl_touch.frame. A client should treat these events as a single + logical touch point update. The order of wl_touch.shape, + wl_touch.orientation and wl_touch.motion is not guaranteed. + A wl_touch.down event is guaranteed to occur before the first + wl_touch.orientation event for this touch ID but both events may occur + within the same wl_touch.frame. - The orientation describes the clockwise angle of a touchpoint's major - axis to the positive surface y-axis and is normalized to the -180 to - +180 degree range. The granularity of orientation depends on the touch - device, some devices only support binary rotation values between 0 and - 90 degrees. + The orientation describes the clockwise angle of a touchpoint's major + axis to the positive surface y-axis and is normalized to the -180 to + +180 degree range. The granularity of orientation depends on the touch + device, some devices only support binary rotation values between 0 and + 90 degrees. - This event is only sent by the compositor if the touch device supports - orientation reports. + This event is only sent by the compositor if the touch device supports + orientation reports. @@ -2772,8 +2870,8 @@ - This enumeration describes how the physical - pixels on an output are laid out. + This enumeration describes how the physical + pixels on an output are laid out. @@ -2785,16 +2883,16 @@ - This describes transformations that clients and compositors apply to - buffer contents. + This describes transformations that clients and compositors apply to + buffer contents. - The flipped values correspond to an initial flip around a - vertical axis followed by rotation. + The flipped values correspond to an initial flip around a + vertical axis followed by rotation. - The purpose is mainly to allow clients to render accordingly and - tell the compositor, so that for fullscreen surfaces, the - compositor will still be able to scan out directly from client - surfaces. + The purpose is mainly to allow clients to render accordingly and + tell the compositor, so that for fullscreen surfaces, the + compositor will still be able to scan out directly from client + surfaces. @@ -2808,91 +2906,91 @@ - The geometry event describes geometric properties of the output. - The event is sent when binding to the output object and whenever - any of the properties change. + The geometry event describes geometric properties of the output. + The event is sent when binding to the output object and whenever + any of the properties change. - The physical size can be set to zero if it doesn't make sense for this - output (e.g. for projectors or virtual outputs). + The physical size can be set to zero if it doesn't make sense for this + output (e.g. for projectors or virtual outputs). - The geometry event will be followed by a done event (starting from - version 2). + The geometry event will be followed by a done event (starting from + version 2). - Clients should use wl_surface.preferred_buffer_transform instead of the - transform advertised by this event to find the preferred buffer - transform to use for a surface. + Clients should use wl_surface.preferred_buffer_transform instead of the + transform advertised by this event to find the preferred buffer + transform to use for a surface. - Note: wl_output only advertises partial information about the output - position and identification. Some compositors, for instance those not - implementing a desktop-style output layout or those exposing virtual - outputs, might fake this information. Instead of using x and y, clients - should use xdg_output.logical_position. Instead of using make and model, - clients should use name and description. + Note: wl_output only advertises partial information about the output + position and identification. Some compositors, for instance those not + implementing a desktop-style output layout or those exposing virtual + outputs, might fake this information. Instead of using x and y, clients + should use xdg_output.logical_position. Instead of using make and model, + clients should use name and description. + summary="x position within the global compositor space"/> + summary="y position within the global compositor space"/> + summary="width in millimeters of the output"/> + summary="height in millimeters of the output"/> + summary="subpixel orientation of the output"/> + summary="textual description of the manufacturer"/> + summary="textual description of the model"/> + summary="additional transformation applied to buffer contents during presentation"/> - These flags describe properties of an output mode. - They are used in the flags bitfield of the mode event. + These flags describe properties of an output mode. + They are used in the flags bitfield of the mode event. + summary="indicates this is the current mode"/> + summary="indicates this is the preferred mode"/> - The mode event describes an available mode for the output. + The mode event describes an available mode for the output. - The event is sent when binding to the output object and there - will always be one mode, the current mode. The event is sent - again if an output changes mode, for the mode that is now - current. In other words, the current mode is always the last - mode that was received with the current flag set. + The event is sent when binding to the output object and there + will always be one mode, the current mode. The event is sent + again if an output changes mode, for the mode that is now + current. In other words, the current mode is always the last + mode that was received with the current flag set. - Non-current modes are deprecated. A compositor can decide to only - advertise the current mode and never send other modes. Clients - should not rely on non-current modes. + Non-current modes are deprecated. A compositor can decide to only + advertise the current mode and never send other modes. Clients + should not rely on non-current modes. - The size of a mode is given in physical hardware units of - the output device. This is not necessarily the same as - the output size in the global compositor space. For instance, - the output may be scaled, as described in wl_output.scale, - or transformed, as described in wl_output.transform. Clients - willing to retrieve the output size in the global compositor - space should use xdg_output.logical_size instead. + The size of a mode is given in physical hardware units of + the output device. This is not necessarily the same as + the output size in the global compositor space. For instance, + the output may be scaled, as described in wl_output.scale, + or transformed, as described in wl_output.transform. Clients + willing to retrieve the output size in the global compositor + space should use xdg_output.logical_size instead. - The vertical refresh rate can be set to zero if it doesn't make - sense for this output (e.g. for virtual outputs). + The vertical refresh rate can be set to zero if it doesn't make + sense for this output (e.g. for virtual outputs). - The mode event will be followed by a done event (starting from - version 2). + The mode event will be followed by a done event (starting from + version 2). - Clients should not use the refresh rate to schedule frames. Instead, - they should use the wl_surface.frame event or the presentation-time - protocol. + Clients should not use the refresh rate to schedule frames. Instead, + they should use the wl_surface.frame event or the presentation-time + protocol. - Note: this information is not always meaningful for all outputs. Some - compositors, such as those exposing virtual outputs, might fake the - refresh rate or the size. + Note: this information is not always meaningful for all outputs. Some + compositors, such as those exposing virtual outputs, might fake the + refresh rate or the size. @@ -2904,34 +3002,34 @@ - This event is sent after all other properties have been - sent after binding to the output object and after any - other property changes done after that. This allows - changes to the output properties to be seen as - atomic, even if they happen via multiple events. + This event is sent after all other properties have been + sent after binding to the output object and after any + other property changes done after that. This allows + changes to the output properties to be seen as + atomic, even if they happen via multiple events. - This event contains scaling geometry information - that is not in the geometry event. It may be sent after - binding the output object or if the output scale changes - later. The compositor will emit a non-zero, positive - value for scale. If it is not sent, the client should - assume a scale of 1. + This event contains scaling geometry information + that is not in the geometry event. It may be sent after + binding the output object or if the output scale changes + later. The compositor will emit a non-zero, positive + value for scale. If it is not sent, the client should + assume a scale of 1. - A scale larger than 1 means that the compositor will - automatically scale surface buffers by this amount - when rendering. This is used for very high resolution - displays where applications rendering at the native - resolution would be too small to be legible. + A scale larger than 1 means that the compositor will + automatically scale surface buffers by this amount + when rendering. This is used for very high resolution + displays where applications rendering at the native + resolution would be too small to be legible. - Clients should use wl_surface.preferred_buffer_scale - instead of this event to find the preferred buffer - scale to use for a surface. + Clients should use wl_surface.preferred_buffer_scale + instead of this event to find the preferred buffer + scale to use for a surface. - The scale event will be followed by a done event. + The scale event will be followed by a done event. @@ -2940,8 +3038,8 @@ - Using this request a client can tell the server that it is not going to - use the output object anymore. + Using this request a client can tell the server that it is not going to + use the output object anymore. @@ -2949,60 +3047,60 @@ - Many compositors will assign user-friendly names to their outputs, show - them to the user, allow the user to refer to an output, etc. The client - may wish to know this name as well to offer the user similar behaviors. + Many compositors will assign user-friendly names to their outputs, show + them to the user, allow the user to refer to an output, etc. The client + may wish to know this name as well to offer the user similar behaviors. - The name is a UTF-8 string with no convention defined for its contents. - Each name is unique among all wl_output globals. The name is only - guaranteed to be unique for the compositor instance. + The name is a UTF-8 string with no convention defined for its contents. + Each name is unique among all wl_output globals. The name is only + guaranteed to be unique for the compositor instance. - The same output name is used for all clients for a given wl_output - global. Thus, the name can be shared across processes to refer to a - specific wl_output global. + The same output name is used for all clients for a given wl_output + global. Thus, the name can be shared across processes to refer to a + specific wl_output global. - The name is not guaranteed to be persistent across sessions, thus cannot - be used to reliably identify an output in e.g. configuration files. + The name is not guaranteed to be persistent across sessions, thus cannot + be used to reliably identify an output in e.g. configuration files. - Examples of names include 'HDMI-A-1', 'WL-1', 'X11-1', etc. However, do - not assume that the name is a reflection of an underlying DRM connector, - X11 connection, etc. + Examples of names include 'HDMI-A-1', 'WL-1', 'X11-1', etc. However, do + not assume that the name is a reflection of an underlying DRM connector, + X11 connection, etc. - The name event is sent after binding the output object. This event is - only sent once per output object, and the name does not change over the - lifetime of the wl_output global. + The name event is sent after binding the output object. This event is + only sent once per output object, and the name does not change over the + lifetime of the wl_output global. - Compositors may re-use the same output name if the wl_output global is - destroyed and re-created later. Compositors should avoid re-using the - same name if possible. + Compositors may re-use the same output name if the wl_output global is + destroyed and re-created later. Compositors should avoid re-using the + same name if possible. - The name event will be followed by a done event. + The name event will be followed by a done event. - Many compositors can produce human-readable descriptions of their - outputs. The client may wish to know this description as well, e.g. for - output selection purposes. + Many compositors can produce human-readable descriptions of their + outputs. The client may wish to know this description as well, e.g. for + output selection purposes. - The description is a UTF-8 string with no convention defined for its - contents. The description is not guaranteed to be unique among all - wl_output globals. Examples might include 'Foocorp 11" Display' or - 'Virtual X11 output via :1'. + The description is a UTF-8 string with no convention defined for its + contents. The description is not guaranteed to be unique among all + wl_output globals. Examples might include 'Foocorp 11" Display' or + 'Virtual X11 output via :1'. - The description event is sent after binding the output object and - whenever the description changes. The description is optional, and may - not be sent at all. + The description event is sent after binding the output object and + whenever the description changes. The description is optional, and may + not be sent at all. - The description event will be followed by a done event. + The description event will be followed by a done event. - + A region object describes an area. @@ -3012,13 +3110,13 @@ - Destroy the region. This will invalidate the object ID. + Destroy the region. This will invalidate the object ID. - Add the specified rectangle to the region. + Add the specified rectangle to the region. @@ -3028,7 +3126,7 @@ - Subtract the specified rectangle from the region. + Subtract the specified rectangle from the region. @@ -3062,47 +3160,47 @@ - Informs the server that the client will not be using this - protocol object anymore. This does not affect any other - objects, wl_subsurface objects included. + Informs the server that the client will not be using this + protocol object anymore. This does not affect any other + objects, wl_subsurface objects included. + summary="the to-be sub-surface is invalid"/> + summary="the to-be sub-surface parent is invalid"/> - Create a sub-surface interface for the given surface, and - associate it with the given parent surface. This turns a - plain wl_surface into a sub-surface. + Create a sub-surface interface for the given surface, and + associate it with the given parent surface. This turns a + plain wl_surface into a sub-surface. - The to-be sub-surface must not already have another role, and it - must not have an existing wl_subsurface object. Otherwise the - bad_surface protocol error is raised. + The to-be sub-surface must not already have another role, and it + must not have an existing wl_subsurface object. Otherwise the + bad_surface protocol error is raised. - Adding sub-surfaces to a parent is a double-buffered operation on the - parent (see wl_surface.commit). The effect of adding a sub-surface - becomes visible on the next time the state of the parent surface is - applied. + Adding sub-surfaces to a parent is a double-buffered operation on the + parent (see wl_surface.commit). The effect of adding a sub-surface + becomes visible on the next time the state of the parent surface is + applied. - The parent surface must not be one of the child surface's descendants, - and the parent must be different from the child surface, otherwise the - bad_parent protocol error is raised. + The parent surface must not be one of the child surface's descendants, + and the parent must be different from the child surface, otherwise the + bad_parent protocol error is raised. - This request modifies the behaviour of wl_surface.commit request on - the sub-surface, see the documentation on wl_subsurface interface. + This request modifies the behaviour of wl_surface.commit request on + the sub-surface, see the documentation on wl_subsurface interface. + summary="the new sub-surface object ID"/> + summary="the surface to be turned into a sub-surface"/> + summary="the parent surface"/> @@ -3120,23 +3218,9 @@ hidden, or if a NULL wl_buffer is applied. These rules apply recursively through the tree of surfaces. - The behaviour of a wl_surface.commit request on a sub-surface - depends on the sub-surface's mode. The possible modes are - synchronized and desynchronized, see methods - wl_subsurface.set_sync and wl_subsurface.set_desync. Synchronized - mode caches the wl_surface state to be applied when the parent's - state gets applied, and desynchronized mode applies the pending - wl_surface state directly. A sub-surface is initially in the - synchronized mode. - - Sub-surfaces also have another kind of state, which is managed by - wl_subsurface requests, as opposed to wl_surface requests. This - state includes the sub-surface position relative to the parent - surface (wl_subsurface.set_position), and the stacking order of - the parent and its sub-surfaces (wl_subsurface.place_above and - .place_below). This state is applied when the parent surface's - wl_surface state is applied, regardless of the sub-surface's mode. - As the exception, set_sync and set_desync are effective immediately. + A sub-surface can be in one of two modes. The possible modes are + synchronized and desynchronized, see methods wl_subsurface.set_sync and + wl_subsurface.set_desync. The main surface can be thought to be always in desynchronized mode, since it does not have a parent in the sub-surfaces sense. @@ -3148,6 +3232,15 @@ synchronized mode, and then assume that all its child and grand-child sub-surfaces are synchronized, too, without explicitly setting them. + If a surface behaves as in synchronized mode, it is effectively + synchronized, otherwise it is effectively desynchronized. + + A sub-surface is initially in the synchronized mode. + + The wl_subsurface interface has requests which modify double-buffered + state of the parent surface (wl_subsurface.set_position, .place_above and + .place_below). + Destroying a sub-surface takes effect immediately. If you need to synchronize the removal of a sub-surface to the parent surface update, unmap the sub-surface first by attaching a NULL wl_buffer, update parent, @@ -3164,34 +3257,32 @@ - The sub-surface interface is removed from the wl_surface object - that was turned into a sub-surface with a - wl_subcompositor.get_subsurface request. The wl_surface's association - to the parent is deleted. The wl_surface is unmapped immediately. + The sub-surface interface is removed from the wl_surface object + that was turned into a sub-surface with a + wl_subcompositor.get_subsurface request. The wl_surface's association + to the parent is deleted. The wl_surface is unmapped immediately. + summary="wl_surface is not a sibling or the parent"/> - This schedules a sub-surface position change. - The sub-surface will be moved so that its origin (top left - corner pixel) will be at the location x, y of the parent surface - coordinate system. The coordinates are not restricted to the parent - surface area. Negative values are allowed. + This sets the position of the sub-surface, relative to the parent + surface. - The scheduled coordinates will take effect whenever the state of the - parent surface is applied. + The sub-surface will be moved so that its origin (top left + corner pixel) will be at the location x, y of the parent surface + coordinate system. The coordinates are not restricted to the parent + surface area. Negative values are allowed. - If more than one set_position request is invoked by the client before - the commit of the parent surface, the position of a new request always - replaces the scheduled position from any previous request. + The initial position is 0, 0. - The initial position is 0, 0. + Position is double-buffered state on the parent surface, see + wl_subsurface and wl_surface.commit for more information. @@ -3199,72 +3290,47 @@ - This sub-surface is taken from the stack, and put back just - above the reference surface, changing the z-order of the sub-surfaces. - The reference surface must be one of the sibling surfaces, or the - parent surface. Using any other surface, including this sub-surface, - will cause a protocol error. + This sub-surface is taken from the stack, and put back just + above the reference surface, changing the z-order of the sub-surfaces. + The reference surface must be one of the sibling surfaces, or the + parent surface. Using any other surface, including this sub-surface, + will cause a protocol error. - The z-order is double-buffered. Requests are handled in order and - applied immediately to a pending state. The final pending state is - copied to the active state the next time the state of the parent - surface is applied. + A new sub-surface is initially added as the top-most in the stack + of its siblings and parent. - A new sub-surface is initially added as the top-most in the stack - of its siblings and parent. + Z-order is double-buffered state on the parent surface, see + wl_subsurface and wl_surface.commit for more information. + summary="the reference surface"/> - The sub-surface is placed just below the reference surface. - See wl_subsurface.place_above. + The sub-surface is placed just below the reference surface. + + See wl_subsurface.place_above. + summary="the reference surface"/> - Change the commit behaviour of the sub-surface to synchronized - mode, also described as the parent dependent mode. + Change the commit behaviour of the sub-surface to synchronized + mode. - In synchronized mode, wl_surface.commit on a sub-surface will - accumulate the committed state in a cache, but the state will - not be applied and hence will not change the compositor output. - The cached state is applied to the sub-surface immediately after - the parent surface's state is applied. This ensures atomic - updates of the parent and all its synchronized sub-surfaces. - Applying the cached state will invalidate the cache, so further - parent surface commits do not (re-)apply old state. - - See wl_subsurface for the recursive effect of this mode. + See wl_subsurface and wl_surface.commit for more information. - Change the commit behaviour of the sub-surface to desynchronized - mode, also described as independent or freely running mode. + Change the commit behaviour of the sub-surface to desynchronized + mode. - In desynchronized mode, wl_surface.commit on a sub-surface will - apply the pending state directly, without caching, as happens - normally with a wl_surface. Calling wl_surface.commit on the - parent surface has no effect on the sub-surface's wl_surface - state. This mode allows a sub-surface to be updated on its own. - - If cached state exists when wl_surface.commit is called in - desynchronized mode, the pending state is added to the cached - state, and applied as a whole. This invalidates the cache. - - Note: even if a sub-surface is set to desynchronized, a parent - sub-surface may override it to behave as synchronized. For details, - see wl_subsurface. - - If a surface's parent surface behaves as desynchronized, then - the cached state is applied on set_desync. + See wl_subsurface and wl_surface.commit for more information. @@ -3281,18 +3347,18 @@ - This request destroys a wl_registry object. + This request destroys a wl_registry object. - The client should no longer use the wl_registry after making this - request. + The client should no longer use the wl_registry after making this + request. - The compositor will emit a wl_display.delete_id event with the object ID - of the registry and will no longer emit any events on the registry. The - client should re-use the object ID once it receives the - wl_display.delete_id event. + The compositor will emit a wl_display.delete_id event with the object ID + of the registry and will no longer emit any events on the registry. The + client should re-use the object ID once it receives the + wl_display.delete_id event. + summary="the registry to destroy"/> diff --git a/include/fennec/platform/linux/wayland/server.h b/include/fennec/platform/linux/wayland/server.h index c644cc4..235bbc5 100644 --- a/include/fennec/platform/linux/wayland/server.h +++ b/include/fennec/platform/linux/wayland/server.h @@ -81,7 +81,7 @@ public: void connect() override; //!< connect to wayland void disconnect() override; //!< disconnect from wayland - bool connected() const override; //!< check if connected to wayland \returns \f$true\f$ if connected, \f$false\f$ otherwise + bool connected() const override; //!< check if connected to wayland \returns \emph{true} if connected, \emph{false} otherwise void dispatch() override; //!< dispatch the current context diff --git a/include/fennec/platform/linux/wayland/vulkan/context.h b/include/fennec/platform/linux/wayland/vulkan/context.h new file mode 100644 index 0000000..1dc7e28 --- /dev/null +++ b/include/fennec/platform/linux/wayland/vulkan/context.h @@ -0,0 +1,74 @@ +// ===================================================================================================================== +// fennec, a free and open source game engine +// Copyright © 2025 Medusa Slockbower +// +// This program is free software: you can redistribute it and/or modify +// it under the terms of the GNU General Public License as published by +// the Free Software Foundation, either version 3 of the License, or +// (at your option) any later version. +// +// This program is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. +// +// You should have received a copy of the GNU General Public License +// along with this program. If not, see . +// ===================================================================================================================== + +/// +/// \file context.h +/// \brief +/// +/// +/// \details +/// \author Medusa Slockbower +/// +/// \copyright Copyright © 2025 - 2026 Medusa Slockbower ([GPLv3](https://www.gnu.org/licenses/gpl-3.0.en.html)) +/// +/// + + +#ifndef FENNEC_PLATFORM_LINUX_WAYLAND_VULKAN_CONTEXT_H +#define FENNEC_PLATFORM_LINUX_WAYLAND_VULKAN_CONTEXT_H + +#include +#include + +namespace fennec +{ + +class wayland_vkcontext : public vkcontext { + +// Definitions & Constants ============================================================================================= +public: + + /// + /// \brief Required Extensions + inline static const dynarray extensions = { + VK_KHR_WAYLAND_SURFACE_EXTENSION_NAME + }; + +// Constructors & Destructor =========================================================================================== +public: + + explicit wayland_vkcontext(display_server* display); + + ~wayland_vkcontext(); + +// Operations ========================================================================================================== +public: + + gfxsurface* create_surface(window* window) override; + + +// Private Member Variables ============================================================================================ +private: + FENNEC_RTTI_CLASS_ENABLE(vkcontext) { + wayland_server::ctx_registry::register_type(); + } +}; + +} + +#endif // FENNEC_PLATFORM_LINUX_WAYLAND_VULKAN_CONTEXT_H diff --git a/include/fennec/platform/linux/wayland/window.h b/include/fennec/platform/linux/wayland/window.h index ca87684..9b3ff0b 100644 --- a/include/fennec/platform/linux/wayland/window.h +++ b/include/fennec/platform/linux/wayland/window.h @@ -76,6 +76,8 @@ public: /// @} + void set_size(const ivec2& size) override; + // Behaviour Flags ===================================================================================================== public: @@ -86,7 +88,7 @@ public: /// \brief sets a specific flag /// \param flag the flag from `window::flag_` /// \param val the value to set the flag to - /// \returns \f$true\f$ on success, \f$false\f$ otherwise + /// \returns \emph{true} on success, \emph{false} otherwise bool set_flag(uint8_t flag, bool val) override; /// @} diff --git a/include/fennec/platform/opengl/egl/context.h b/include/fennec/platform/opengl/egl/context.h index c67bd2b..bf2cedd 100644 --- a/include/fennec/platform/opengl/egl/context.h +++ b/include/fennec/platform/opengl/egl/context.h @@ -66,7 +66,7 @@ public: // /// - /// \returns \f$true\f$ if the context is valid, \f$false\f$ otherwise + /// \returns \emph{true} if the context is valid, \emph{false} otherwise bool is_valid() override; private: diff --git a/include/fennec/platform/opengl/egl/error.h b/include/fennec/platform/opengl/egl/error.h index 91d77b5..f0cec90 100644 --- a/include/fennec/platform/opengl/egl/error.h +++ b/include/fennec/platform/opengl/egl/error.h @@ -37,7 +37,7 @@ /// \brief convert egl error to a readable string /// \param err the error code -/// \returns the error string corresponding to \f$err\f$ +/// \returns the error string corresponding to \emph{err} inline fennec::cstring eglErrorString(EGLint err) { switch (err) { case EGL_SUCCESS: return "None"; diff --git a/include/fennec/platform/vulkan/volk/volk.h b/include/fennec/platform/vulkan/volk/volk.h new file mode 100644 index 0000000..20a5bb4 --- /dev/null +++ b/include/fennec/platform/vulkan/volk/volk.h @@ -0,0 +1,2176 @@ +/** + * volk + * + * Copyright (C) 2018-2024, by Arseny Kapoulkine (arseny.kapoulkine@gmail.com) + * Report bugs and download new versions at https://github.com/zeux/volk + * + * This library is distributed under the MIT License. See notice at the end of this file. + */ +/* clang-format off */ +#ifndef VOLK_H_ +#define VOLK_H_ + +#if defined(VULKAN_H_) && !defined(VK_NO_PROTOTYPES) +# error To use volk, you need to define VK_NO_PROTOTYPES before including vulkan.h +#endif + +/* VOLK_GENERATE_VERSION_DEFINE */ +#define VOLK_HEADER_VERSION 304 +/* VOLK_GENERATE_VERSION_DEFINE */ + +#ifndef VK_NO_PROTOTYPES +# define VK_NO_PROTOTYPES +#endif + +#ifndef VULKAN_H_ +# ifdef VOLK_VULKAN_H_PATH +# include VOLK_VULKAN_H_PATH +# elif defined(VK_USE_PLATFORM_WIN32_KHR) +# include +# include + + /* When VK_USE_PLATFORM_WIN32_KHR is defined, instead of including vulkan.h directly, we include individual parts of the SDK + * This is necessary to avoid including which is very heavy - it takes 200ms to parse without WIN32_LEAN_AND_MEAN + * and 100ms to parse with it. vulkan_win32.h only needs a few symbols that are easy to redefine ourselves. + */ + typedef unsigned long DWORD; + typedef const wchar_t* LPCWSTR; + typedef void* HANDLE; + typedef struct HINSTANCE__* HINSTANCE; + typedef struct HWND__* HWND; + typedef struct HMONITOR__* HMONITOR; + typedef struct _SECURITY_ATTRIBUTES SECURITY_ATTRIBUTES; + +# include + +# ifdef VK_ENABLE_BETA_EXTENSIONS +# include +# endif +# else +# include +# endif +#endif + +#ifdef __cplusplus +extern "C" { +#endif + +struct VolkDeviceTable; + +/** + * Initialize library by loading Vulkan loader; call this function before creating the Vulkan instance. + * + * Returns VK_SUCCESS on success and VK_ERROR_INITIALIZATION_FAILED otherwise. + */ +VkResult volkInitialize(void); + +/** + * Initialize library by providing a custom handler to load global symbols. + * + * This function can be used instead of volkInitialize. + * The handler function pointer will be asked to load global Vulkan symbols which require no instance + * (such as vkCreateInstance, vkEnumerateInstance* and vkEnumerateInstanceVersion if available). + */ +void volkInitializeCustom(PFN_vkGetInstanceProcAddr handler); + +/** + * Finalize library by unloading Vulkan loader and resetting global symbols to NULL. + * + * This function does not need to be called on process exit (as loader will be unloaded automatically) or if volkInitialize failed. + * In general this function is optional to call but may be useful in rare cases eg if volk needs to be reinitialized multiple times. + */ +void volkFinalize(void); + +/** + * Get Vulkan instance version supported by the Vulkan loader, or 0 if Vulkan isn't supported + * + * Returns 0 if volkInitialize wasn't called or failed. + */ +uint32_t volkGetInstanceVersion(void); + +/** + * Load global function pointers using application-created VkInstance; call this function after creating the Vulkan instance. + */ +void volkLoadInstance(VkInstance instance); + +/** + * Load global function pointers using application-created VkInstance; call this function after creating the Vulkan instance. + * Skips loading device-based function pointers, requires usage of volkLoadDevice afterwards. + */ +void volkLoadInstanceOnly(VkInstance instance); + +/** + * Load global function pointers using application-created VkDevice; call this function after creating the Vulkan device. + * + * Note: this is not suitable for applications that want to use multiple VkDevice objects concurrently. + */ +void volkLoadDevice(VkDevice device); + +/** + * Return last VkInstance for which global function pointers have been loaded via volkLoadInstance(), + * or VK_NULL_HANDLE if volkLoadInstance() has not been called. + */ +VkInstance volkGetLoadedInstance(void); + +/** + * Return last VkDevice for which global function pointers have been loaded via volkLoadDevice(), + * or VK_NULL_HANDLE if volkLoadDevice() has not been called. + */ +VkDevice volkGetLoadedDevice(void); + +/** + * Load function pointers using application-created VkDevice into a table. + * Application should use function pointers from that table instead of using global function pointers. + */ +void volkLoadDeviceTable(struct VolkDeviceTable* table, VkDevice device); + +/** + * Device-specific function pointer table + */ +struct VolkDeviceTable +{ + /* VOLK_GENERATE_DEVICE_TABLE */ +#if defined(VK_VERSION_1_0) + PFN_vkAllocateCommandBuffers vkAllocateCommandBuffers; + PFN_vkAllocateDescriptorSets vkAllocateDescriptorSets; + PFN_vkAllocateMemory vkAllocateMemory; + PFN_vkBeginCommandBuffer vkBeginCommandBuffer; + PFN_vkBindBufferMemory vkBindBufferMemory; + PFN_vkBindImageMemory vkBindImageMemory; + PFN_vkCmdBeginQuery vkCmdBeginQuery; + PFN_vkCmdBeginRenderPass vkCmdBeginRenderPass; + PFN_vkCmdBindDescriptorSets vkCmdBindDescriptorSets; + PFN_vkCmdBindIndexBuffer vkCmdBindIndexBuffer; + PFN_vkCmdBindPipeline vkCmdBindPipeline; + PFN_vkCmdBindVertexBuffers vkCmdBindVertexBuffers; + PFN_vkCmdBlitImage vkCmdBlitImage; + PFN_vkCmdClearAttachments vkCmdClearAttachments; + PFN_vkCmdClearColorImage vkCmdClearColorImage; + PFN_vkCmdClearDepthStencilImage vkCmdClearDepthStencilImage; + PFN_vkCmdCopyBuffer vkCmdCopyBuffer; + PFN_vkCmdCopyBufferToImage vkCmdCopyBufferToImage; + PFN_vkCmdCopyImage vkCmdCopyImage; + PFN_vkCmdCopyImageToBuffer vkCmdCopyImageToBuffer; + PFN_vkCmdCopyQueryPoolResults vkCmdCopyQueryPoolResults; + PFN_vkCmdDispatch vkCmdDispatch; + PFN_vkCmdDispatchIndirect vkCmdDispatchIndirect; + PFN_vkCmdDraw vkCmdDraw; + PFN_vkCmdDrawIndexed vkCmdDrawIndexed; + PFN_vkCmdDrawIndexedIndirect vkCmdDrawIndexedIndirect; + PFN_vkCmdDrawIndirect vkCmdDrawIndirect; + PFN_vkCmdEndQuery vkCmdEndQuery; + PFN_vkCmdEndRenderPass vkCmdEndRenderPass; + PFN_vkCmdExecuteCommands vkCmdExecuteCommands; + PFN_vkCmdFillBuffer vkCmdFillBuffer; + PFN_vkCmdNextSubpass vkCmdNextSubpass; + PFN_vkCmdPipelineBarrier vkCmdPipelineBarrier; + PFN_vkCmdPushConstants vkCmdPushConstants; + PFN_vkCmdResetEvent vkCmdResetEvent; + PFN_vkCmdResetQueryPool vkCmdResetQueryPool; + PFN_vkCmdResolveImage vkCmdResolveImage; + PFN_vkCmdSetBlendConstants vkCmdSetBlendConstants; + PFN_vkCmdSetDepthBias vkCmdSetDepthBias; + PFN_vkCmdSetDepthBounds vkCmdSetDepthBounds; + PFN_vkCmdSetEvent vkCmdSetEvent; + PFN_vkCmdSetLineWidth vkCmdSetLineWidth; + PFN_vkCmdSetScissor vkCmdSetScissor; + PFN_vkCmdSetStencilCompareMask vkCmdSetStencilCompareMask; + PFN_vkCmdSetStencilReference vkCmdSetStencilReference; + PFN_vkCmdSetStencilWriteMask vkCmdSetStencilWriteMask; + PFN_vkCmdSetViewport vkCmdSetViewport; + PFN_vkCmdUpdateBuffer vkCmdUpdateBuffer; + PFN_vkCmdWaitEvents vkCmdWaitEvents; + PFN_vkCmdWriteTimestamp vkCmdWriteTimestamp; + PFN_vkCreateBuffer vkCreateBuffer; + PFN_vkCreateBufferView vkCreateBufferView; + PFN_vkCreateCommandPool vkCreateCommandPool; + PFN_vkCreateComputePipelines vkCreateComputePipelines; + PFN_vkCreateDescriptorPool vkCreateDescriptorPool; + PFN_vkCreateDescriptorSetLayout vkCreateDescriptorSetLayout; + PFN_vkCreateEvent vkCreateEvent; + PFN_vkCreateFence vkCreateFence; + PFN_vkCreateFramebuffer vkCreateFramebuffer; + PFN_vkCreateGraphicsPipelines vkCreateGraphicsPipelines; + PFN_vkCreateImage vkCreateImage; + PFN_vkCreateImageView vkCreateImageView; + PFN_vkCreatePipelineCache vkCreatePipelineCache; + PFN_vkCreatePipelineLayout vkCreatePipelineLayout; + PFN_vkCreateQueryPool vkCreateQueryPool; + PFN_vkCreateRenderPass vkCreateRenderPass; + PFN_vkCreateSampler vkCreateSampler; + PFN_vkCreateSemaphore vkCreateSemaphore; + PFN_vkCreateShaderModule vkCreateShaderModule; + PFN_vkDestroyBuffer vkDestroyBuffer; + PFN_vkDestroyBufferView vkDestroyBufferView; + PFN_vkDestroyCommandPool vkDestroyCommandPool; + PFN_vkDestroyDescriptorPool vkDestroyDescriptorPool; + PFN_vkDestroyDescriptorSetLayout vkDestroyDescriptorSetLayout; + PFN_vkDestroyDevice vkDestroyDevice; + PFN_vkDestroyEvent vkDestroyEvent; + PFN_vkDestroyFence vkDestroyFence; + PFN_vkDestroyFramebuffer vkDestroyFramebuffer; + PFN_vkDestroyImage vkDestroyImage; + PFN_vkDestroyImageView vkDestroyImageView; + PFN_vkDestroyPipeline vkDestroyPipeline; + PFN_vkDestroyPipelineCache vkDestroyPipelineCache; + PFN_vkDestroyPipelineLayout vkDestroyPipelineLayout; + PFN_vkDestroyQueryPool vkDestroyQueryPool; + PFN_vkDestroyRenderPass vkDestroyRenderPass; + PFN_vkDestroySampler vkDestroySampler; + PFN_vkDestroySemaphore vkDestroySemaphore; + PFN_vkDestroyShaderModule vkDestroyShaderModule; + PFN_vkDeviceWaitIdle vkDeviceWaitIdle; + PFN_vkEndCommandBuffer vkEndCommandBuffer; + PFN_vkFlushMappedMemoryRanges vkFlushMappedMemoryRanges; + PFN_vkFreeCommandBuffers vkFreeCommandBuffers; + PFN_vkFreeDescriptorSets vkFreeDescriptorSets; + PFN_vkFreeMemory vkFreeMemory; + PFN_vkGetBufferMemoryRequirements vkGetBufferMemoryRequirements; + PFN_vkGetDeviceMemoryCommitment vkGetDeviceMemoryCommitment; + PFN_vkGetDeviceQueue vkGetDeviceQueue; + PFN_vkGetEventStatus vkGetEventStatus; + PFN_vkGetFenceStatus vkGetFenceStatus; + PFN_vkGetImageMemoryRequirements vkGetImageMemoryRequirements; + PFN_vkGetImageSparseMemoryRequirements vkGetImageSparseMemoryRequirements; + PFN_vkGetImageSubresourceLayout vkGetImageSubresourceLayout; + PFN_vkGetPipelineCacheData vkGetPipelineCacheData; + PFN_vkGetQueryPoolResults vkGetQueryPoolResults; + PFN_vkGetRenderAreaGranularity vkGetRenderAreaGranularity; + PFN_vkInvalidateMappedMemoryRanges vkInvalidateMappedMemoryRanges; + PFN_vkMapMemory vkMapMemory; + PFN_vkMergePipelineCaches vkMergePipelineCaches; + PFN_vkQueueBindSparse vkQueueBindSparse; + PFN_vkQueueSubmit vkQueueSubmit; + PFN_vkQueueWaitIdle vkQueueWaitIdle; + PFN_vkResetCommandBuffer vkResetCommandBuffer; + PFN_vkResetCommandPool vkResetCommandPool; + PFN_vkResetDescriptorPool vkResetDescriptorPool; + PFN_vkResetEvent vkResetEvent; + PFN_vkResetFences vkResetFences; + PFN_vkSetEvent vkSetEvent; + PFN_vkUnmapMemory vkUnmapMemory; + PFN_vkUpdateDescriptorSets vkUpdateDescriptorSets; + PFN_vkWaitForFences vkWaitForFences; +#endif /* defined(VK_VERSION_1_0) */ +#if defined(VK_VERSION_1_1) + PFN_vkBindBufferMemory2 vkBindBufferMemory2; + PFN_vkBindImageMemory2 vkBindImageMemory2; + PFN_vkCmdDispatchBase vkCmdDispatchBase; + PFN_vkCmdSetDeviceMask vkCmdSetDeviceMask; + PFN_vkCreateDescriptorUpdateTemplate vkCreateDescriptorUpdateTemplate; + PFN_vkCreateSamplerYcbcrConversion vkCreateSamplerYcbcrConversion; + PFN_vkDestroyDescriptorUpdateTemplate vkDestroyDescriptorUpdateTemplate; + PFN_vkDestroySamplerYcbcrConversion vkDestroySamplerYcbcrConversion; + PFN_vkGetBufferMemoryRequirements2 vkGetBufferMemoryRequirements2; + PFN_vkGetDescriptorSetLayoutSupport vkGetDescriptorSetLayoutSupport; + PFN_vkGetDeviceGroupPeerMemoryFeatures vkGetDeviceGroupPeerMemoryFeatures; + PFN_vkGetDeviceQueue2 vkGetDeviceQueue2; + PFN_vkGetImageMemoryRequirements2 vkGetImageMemoryRequirements2; + PFN_vkGetImageSparseMemoryRequirements2 vkGetImageSparseMemoryRequirements2; + PFN_vkTrimCommandPool vkTrimCommandPool; + PFN_vkUpdateDescriptorSetWithTemplate vkUpdateDescriptorSetWithTemplate; +#endif /* defined(VK_VERSION_1_1) */ +#if defined(VK_VERSION_1_2) + PFN_vkCmdBeginRenderPass2 vkCmdBeginRenderPass2; + PFN_vkCmdDrawIndexedIndirectCount vkCmdDrawIndexedIndirectCount; + PFN_vkCmdDrawIndirectCount vkCmdDrawIndirectCount; + PFN_vkCmdEndRenderPass2 vkCmdEndRenderPass2; + PFN_vkCmdNextSubpass2 vkCmdNextSubpass2; + PFN_vkCreateRenderPass2 vkCreateRenderPass2; + PFN_vkGetBufferDeviceAddress vkGetBufferDeviceAddress; + PFN_vkGetBufferOpaqueCaptureAddress vkGetBufferOpaqueCaptureAddress; + PFN_vkGetDeviceMemoryOpaqueCaptureAddress vkGetDeviceMemoryOpaqueCaptureAddress; + PFN_vkGetSemaphoreCounterValue vkGetSemaphoreCounterValue; + PFN_vkResetQueryPool vkResetQueryPool; + PFN_vkSignalSemaphore vkSignalSemaphore; + PFN_vkWaitSemaphores vkWaitSemaphores; +#endif /* defined(VK_VERSION_1_2) */ +#if defined(VK_VERSION_1_3) + PFN_vkCmdBeginRendering vkCmdBeginRendering; + PFN_vkCmdBindVertexBuffers2 vkCmdBindVertexBuffers2; + PFN_vkCmdBlitImage2 vkCmdBlitImage2; + PFN_vkCmdCopyBuffer2 vkCmdCopyBuffer2; + PFN_vkCmdCopyBufferToImage2 vkCmdCopyBufferToImage2; + PFN_vkCmdCopyImage2 vkCmdCopyImage2; + PFN_vkCmdCopyImageToBuffer2 vkCmdCopyImageToBuffer2; + PFN_vkCmdEndRendering vkCmdEndRendering; + PFN_vkCmdPipelineBarrier2 vkCmdPipelineBarrier2; + PFN_vkCmdResetEvent2 vkCmdResetEvent2; + PFN_vkCmdResolveImage2 vkCmdResolveImage2; + PFN_vkCmdSetCullMode vkCmdSetCullMode; + PFN_vkCmdSetDepthBiasEnable vkCmdSetDepthBiasEnable; + PFN_vkCmdSetDepthBoundsTestEnable vkCmdSetDepthBoundsTestEnable; + PFN_vkCmdSetDepthCompareOp vkCmdSetDepthCompareOp; + PFN_vkCmdSetDepthTestEnable vkCmdSetDepthTestEnable; + PFN_vkCmdSetDepthWriteEnable vkCmdSetDepthWriteEnable; + PFN_vkCmdSetEvent2 vkCmdSetEvent2; + PFN_vkCmdSetFrontFace vkCmdSetFrontFace; + PFN_vkCmdSetPrimitiveRestartEnable vkCmdSetPrimitiveRestartEnable; + PFN_vkCmdSetPrimitiveTopology vkCmdSetPrimitiveTopology; + PFN_vkCmdSetRasterizerDiscardEnable vkCmdSetRasterizerDiscardEnable; + PFN_vkCmdSetScissorWithCount vkCmdSetScissorWithCount; + PFN_vkCmdSetStencilOp vkCmdSetStencilOp; + PFN_vkCmdSetStencilTestEnable vkCmdSetStencilTestEnable; + PFN_vkCmdSetViewportWithCount vkCmdSetViewportWithCount; + PFN_vkCmdWaitEvents2 vkCmdWaitEvents2; + PFN_vkCmdWriteTimestamp2 vkCmdWriteTimestamp2; + PFN_vkCreatePrivateDataSlot vkCreatePrivateDataSlot; + PFN_vkDestroyPrivateDataSlot vkDestroyPrivateDataSlot; + PFN_vkGetDeviceBufferMemoryRequirements vkGetDeviceBufferMemoryRequirements; + PFN_vkGetDeviceImageMemoryRequirements vkGetDeviceImageMemoryRequirements; + PFN_vkGetDeviceImageSparseMemoryRequirements vkGetDeviceImageSparseMemoryRequirements; + PFN_vkGetPrivateData vkGetPrivateData; + PFN_vkQueueSubmit2 vkQueueSubmit2; + PFN_vkSetPrivateData vkSetPrivateData; +#endif /* defined(VK_VERSION_1_3) */ +#if defined(VK_VERSION_1_4) + PFN_vkCmdBindDescriptorSets2 vkCmdBindDescriptorSets2; + PFN_vkCmdBindIndexBuffer2 vkCmdBindIndexBuffer2; + PFN_vkCmdPushConstants2 vkCmdPushConstants2; + PFN_vkCmdPushDescriptorSet vkCmdPushDescriptorSet; + PFN_vkCmdPushDescriptorSet2 vkCmdPushDescriptorSet2; + PFN_vkCmdPushDescriptorSetWithTemplate vkCmdPushDescriptorSetWithTemplate; + PFN_vkCmdPushDescriptorSetWithTemplate2 vkCmdPushDescriptorSetWithTemplate2; + PFN_vkCmdSetLineStipple vkCmdSetLineStipple; + PFN_vkCmdSetRenderingAttachmentLocations vkCmdSetRenderingAttachmentLocations; + PFN_vkCmdSetRenderingInputAttachmentIndices vkCmdSetRenderingInputAttachmentIndices; + PFN_vkCopyImageToImage vkCopyImageToImage; + PFN_vkCopyImageToMemory vkCopyImageToMemory; + PFN_vkCopyMemoryToImage vkCopyMemoryToImage; + PFN_vkGetDeviceImageSubresourceLayout vkGetDeviceImageSubresourceLayout; + PFN_vkGetImageSubresourceLayout2 vkGetImageSubresourceLayout2; + PFN_vkGetRenderingAreaGranularity vkGetRenderingAreaGranularity; + PFN_vkMapMemory2 vkMapMemory2; + PFN_vkTransitionImageLayout vkTransitionImageLayout; + PFN_vkUnmapMemory2 vkUnmapMemory2; +#endif /* defined(VK_VERSION_1_4) */ +#if defined(VK_AMDX_shader_enqueue) + PFN_vkCmdDispatchGraphAMDX vkCmdDispatchGraphAMDX; + PFN_vkCmdDispatchGraphIndirectAMDX vkCmdDispatchGraphIndirectAMDX; + PFN_vkCmdDispatchGraphIndirectCountAMDX vkCmdDispatchGraphIndirectCountAMDX; + PFN_vkCmdInitializeGraphScratchMemoryAMDX vkCmdInitializeGraphScratchMemoryAMDX; + PFN_vkCreateExecutionGraphPipelinesAMDX vkCreateExecutionGraphPipelinesAMDX; + PFN_vkGetExecutionGraphPipelineNodeIndexAMDX vkGetExecutionGraphPipelineNodeIndexAMDX; + PFN_vkGetExecutionGraphPipelineScratchSizeAMDX vkGetExecutionGraphPipelineScratchSizeAMDX; +#endif /* defined(VK_AMDX_shader_enqueue) */ +#if defined(VK_AMD_anti_lag) + PFN_vkAntiLagUpdateAMD vkAntiLagUpdateAMD; +#endif /* defined(VK_AMD_anti_lag) */ +#if defined(VK_AMD_buffer_marker) + PFN_vkCmdWriteBufferMarkerAMD vkCmdWriteBufferMarkerAMD; +#endif /* defined(VK_AMD_buffer_marker) */ +#if defined(VK_AMD_buffer_marker) && (defined(VK_VERSION_1_3) || defined(VK_KHR_synchronization2)) + PFN_vkCmdWriteBufferMarker2AMD vkCmdWriteBufferMarker2AMD; +#endif /* defined(VK_AMD_buffer_marker) && (defined(VK_VERSION_1_3) || defined(VK_KHR_synchronization2)) */ +#if defined(VK_AMD_display_native_hdr) + PFN_vkSetLocalDimmingAMD vkSetLocalDimmingAMD; +#endif /* defined(VK_AMD_display_native_hdr) */ +#if defined(VK_AMD_draw_indirect_count) + PFN_vkCmdDrawIndexedIndirectCountAMD vkCmdDrawIndexedIndirectCountAMD; + PFN_vkCmdDrawIndirectCountAMD vkCmdDrawIndirectCountAMD; +#endif /* defined(VK_AMD_draw_indirect_count) */ +#if defined(VK_AMD_shader_info) + PFN_vkGetShaderInfoAMD vkGetShaderInfoAMD; +#endif /* defined(VK_AMD_shader_info) */ +#if defined(VK_ANDROID_external_memory_android_hardware_buffer) + PFN_vkGetAndroidHardwareBufferPropertiesANDROID vkGetAndroidHardwareBufferPropertiesANDROID; + PFN_vkGetMemoryAndroidHardwareBufferANDROID vkGetMemoryAndroidHardwareBufferANDROID; +#endif /* defined(VK_ANDROID_external_memory_android_hardware_buffer) */ +#if defined(VK_EXT_attachment_feedback_loop_dynamic_state) + PFN_vkCmdSetAttachmentFeedbackLoopEnableEXT vkCmdSetAttachmentFeedbackLoopEnableEXT; +#endif /* defined(VK_EXT_attachment_feedback_loop_dynamic_state) */ +#if defined(VK_EXT_buffer_device_address) + PFN_vkGetBufferDeviceAddressEXT vkGetBufferDeviceAddressEXT; +#endif /* defined(VK_EXT_buffer_device_address) */ +#if defined(VK_EXT_calibrated_timestamps) + PFN_vkGetCalibratedTimestampsEXT vkGetCalibratedTimestampsEXT; +#endif /* defined(VK_EXT_calibrated_timestamps) */ +#if defined(VK_EXT_color_write_enable) + PFN_vkCmdSetColorWriteEnableEXT vkCmdSetColorWriteEnableEXT; +#endif /* defined(VK_EXT_color_write_enable) */ +#if defined(VK_EXT_conditional_rendering) + PFN_vkCmdBeginConditionalRenderingEXT vkCmdBeginConditionalRenderingEXT; + PFN_vkCmdEndConditionalRenderingEXT vkCmdEndConditionalRenderingEXT; +#endif /* defined(VK_EXT_conditional_rendering) */ +#if defined(VK_EXT_debug_marker) + PFN_vkCmdDebugMarkerBeginEXT vkCmdDebugMarkerBeginEXT; + PFN_vkCmdDebugMarkerEndEXT vkCmdDebugMarkerEndEXT; + PFN_vkCmdDebugMarkerInsertEXT vkCmdDebugMarkerInsertEXT; + PFN_vkDebugMarkerSetObjectNameEXT vkDebugMarkerSetObjectNameEXT; + PFN_vkDebugMarkerSetObjectTagEXT vkDebugMarkerSetObjectTagEXT; +#endif /* defined(VK_EXT_debug_marker) */ +#if defined(VK_EXT_depth_bias_control) + PFN_vkCmdSetDepthBias2EXT vkCmdSetDepthBias2EXT; +#endif /* defined(VK_EXT_depth_bias_control) */ +#if defined(VK_EXT_descriptor_buffer) + PFN_vkCmdBindDescriptorBufferEmbeddedSamplersEXT vkCmdBindDescriptorBufferEmbeddedSamplersEXT; + PFN_vkCmdBindDescriptorBuffersEXT vkCmdBindDescriptorBuffersEXT; + PFN_vkCmdSetDescriptorBufferOffsetsEXT vkCmdSetDescriptorBufferOffsetsEXT; + PFN_vkGetBufferOpaqueCaptureDescriptorDataEXT vkGetBufferOpaqueCaptureDescriptorDataEXT; + PFN_vkGetDescriptorEXT vkGetDescriptorEXT; + PFN_vkGetDescriptorSetLayoutBindingOffsetEXT vkGetDescriptorSetLayoutBindingOffsetEXT; + PFN_vkGetDescriptorSetLayoutSizeEXT vkGetDescriptorSetLayoutSizeEXT; + PFN_vkGetImageOpaqueCaptureDescriptorDataEXT vkGetImageOpaqueCaptureDescriptorDataEXT; + PFN_vkGetImageViewOpaqueCaptureDescriptorDataEXT vkGetImageViewOpaqueCaptureDescriptorDataEXT; + PFN_vkGetSamplerOpaqueCaptureDescriptorDataEXT vkGetSamplerOpaqueCaptureDescriptorDataEXT; +#endif /* defined(VK_EXT_descriptor_buffer) */ +#if defined(VK_EXT_descriptor_buffer) && (defined(VK_KHR_acceleration_structure) || defined(VK_NV_ray_tracing)) + PFN_vkGetAccelerationStructureOpaqueCaptureDescriptorDataEXT vkGetAccelerationStructureOpaqueCaptureDescriptorDataEXT; +#endif /* defined(VK_EXT_descriptor_buffer) && (defined(VK_KHR_acceleration_structure) || defined(VK_NV_ray_tracing)) */ +#if defined(VK_EXT_device_fault) + PFN_vkGetDeviceFaultInfoEXT vkGetDeviceFaultInfoEXT; +#endif /* defined(VK_EXT_device_fault) */ +#if defined(VK_EXT_device_generated_commands) + PFN_vkCmdExecuteGeneratedCommandsEXT vkCmdExecuteGeneratedCommandsEXT; + PFN_vkCmdPreprocessGeneratedCommandsEXT vkCmdPreprocessGeneratedCommandsEXT; + PFN_vkCreateIndirectCommandsLayoutEXT vkCreateIndirectCommandsLayoutEXT; + PFN_vkCreateIndirectExecutionSetEXT vkCreateIndirectExecutionSetEXT; + PFN_vkDestroyIndirectCommandsLayoutEXT vkDestroyIndirectCommandsLayoutEXT; + PFN_vkDestroyIndirectExecutionSetEXT vkDestroyIndirectExecutionSetEXT; + PFN_vkGetGeneratedCommandsMemoryRequirementsEXT vkGetGeneratedCommandsMemoryRequirementsEXT; + PFN_vkUpdateIndirectExecutionSetPipelineEXT vkUpdateIndirectExecutionSetPipelineEXT; + PFN_vkUpdateIndirectExecutionSetShaderEXT vkUpdateIndirectExecutionSetShaderEXT; +#endif /* defined(VK_EXT_device_generated_commands) */ +#if defined(VK_EXT_discard_rectangles) + PFN_vkCmdSetDiscardRectangleEXT vkCmdSetDiscardRectangleEXT; +#endif /* defined(VK_EXT_discard_rectangles) */ +#if defined(VK_EXT_discard_rectangles) && VK_EXT_DISCARD_RECTANGLES_SPEC_VERSION >= 2 + PFN_vkCmdSetDiscardRectangleEnableEXT vkCmdSetDiscardRectangleEnableEXT; + PFN_vkCmdSetDiscardRectangleModeEXT vkCmdSetDiscardRectangleModeEXT; +#endif /* defined(VK_EXT_discard_rectangles) && VK_EXT_DISCARD_RECTANGLES_SPEC_VERSION >= 2 */ +#if defined(VK_EXT_display_control) + PFN_vkDisplayPowerControlEXT vkDisplayPowerControlEXT; + PFN_vkGetSwapchainCounterEXT vkGetSwapchainCounterEXT; + PFN_vkRegisterDeviceEventEXT vkRegisterDeviceEventEXT; + PFN_vkRegisterDisplayEventEXT vkRegisterDisplayEventEXT; +#endif /* defined(VK_EXT_display_control) */ +#if defined(VK_EXT_external_memory_host) + PFN_vkGetMemoryHostPointerPropertiesEXT vkGetMemoryHostPointerPropertiesEXT; +#endif /* defined(VK_EXT_external_memory_host) */ +#if defined(VK_EXT_full_screen_exclusive) + PFN_vkAcquireFullScreenExclusiveModeEXT vkAcquireFullScreenExclusiveModeEXT; + PFN_vkReleaseFullScreenExclusiveModeEXT vkReleaseFullScreenExclusiveModeEXT; +#endif /* defined(VK_EXT_full_screen_exclusive) */ +#if defined(VK_EXT_full_screen_exclusive) && (defined(VK_KHR_device_group) || defined(VK_VERSION_1_1)) + PFN_vkGetDeviceGroupSurfacePresentModes2EXT vkGetDeviceGroupSurfacePresentModes2EXT; +#endif /* defined(VK_EXT_full_screen_exclusive) && (defined(VK_KHR_device_group) || defined(VK_VERSION_1_1)) */ +#if defined(VK_EXT_hdr_metadata) + PFN_vkSetHdrMetadataEXT vkSetHdrMetadataEXT; +#endif /* defined(VK_EXT_hdr_metadata) */ +#if defined(VK_EXT_host_image_copy) + PFN_vkCopyImageToImageEXT vkCopyImageToImageEXT; + PFN_vkCopyImageToMemoryEXT vkCopyImageToMemoryEXT; + PFN_vkCopyMemoryToImageEXT vkCopyMemoryToImageEXT; + PFN_vkTransitionImageLayoutEXT vkTransitionImageLayoutEXT; +#endif /* defined(VK_EXT_host_image_copy) */ +#if defined(VK_EXT_host_query_reset) + PFN_vkResetQueryPoolEXT vkResetQueryPoolEXT; +#endif /* defined(VK_EXT_host_query_reset) */ +#if defined(VK_EXT_image_drm_format_modifier) + PFN_vkGetImageDrmFormatModifierPropertiesEXT vkGetImageDrmFormatModifierPropertiesEXT; +#endif /* defined(VK_EXT_image_drm_format_modifier) */ +#if defined(VK_EXT_line_rasterization) + PFN_vkCmdSetLineStippleEXT vkCmdSetLineStippleEXT; +#endif /* defined(VK_EXT_line_rasterization) */ +#if defined(VK_EXT_mesh_shader) + PFN_vkCmdDrawMeshTasksEXT vkCmdDrawMeshTasksEXT; + PFN_vkCmdDrawMeshTasksIndirectEXT vkCmdDrawMeshTasksIndirectEXT; +#endif /* defined(VK_EXT_mesh_shader) */ +#if defined(VK_EXT_mesh_shader) && (defined(VK_KHR_draw_indirect_count) || defined(VK_VERSION_1_2)) + PFN_vkCmdDrawMeshTasksIndirectCountEXT vkCmdDrawMeshTasksIndirectCountEXT; +#endif /* defined(VK_EXT_mesh_shader) && (defined(VK_KHR_draw_indirect_count) || defined(VK_VERSION_1_2)) */ +#if defined(VK_EXT_metal_objects) + PFN_vkExportMetalObjectsEXT vkExportMetalObjectsEXT; +#endif /* defined(VK_EXT_metal_objects) */ +#if defined(VK_EXT_multi_draw) + PFN_vkCmdDrawMultiEXT vkCmdDrawMultiEXT; + PFN_vkCmdDrawMultiIndexedEXT vkCmdDrawMultiIndexedEXT; +#endif /* defined(VK_EXT_multi_draw) */ +#if defined(VK_EXT_opacity_micromap) + PFN_vkBuildMicromapsEXT vkBuildMicromapsEXT; + PFN_vkCmdBuildMicromapsEXT vkCmdBuildMicromapsEXT; + PFN_vkCmdCopyMemoryToMicromapEXT vkCmdCopyMemoryToMicromapEXT; + PFN_vkCmdCopyMicromapEXT vkCmdCopyMicromapEXT; + PFN_vkCmdCopyMicromapToMemoryEXT vkCmdCopyMicromapToMemoryEXT; + PFN_vkCmdWriteMicromapsPropertiesEXT vkCmdWriteMicromapsPropertiesEXT; + PFN_vkCopyMemoryToMicromapEXT vkCopyMemoryToMicromapEXT; + PFN_vkCopyMicromapEXT vkCopyMicromapEXT; + PFN_vkCopyMicromapToMemoryEXT vkCopyMicromapToMemoryEXT; + PFN_vkCreateMicromapEXT vkCreateMicromapEXT; + PFN_vkDestroyMicromapEXT vkDestroyMicromapEXT; + PFN_vkGetDeviceMicromapCompatibilityEXT vkGetDeviceMicromapCompatibilityEXT; + PFN_vkGetMicromapBuildSizesEXT vkGetMicromapBuildSizesEXT; + PFN_vkWriteMicromapsPropertiesEXT vkWriteMicromapsPropertiesEXT; +#endif /* defined(VK_EXT_opacity_micromap) */ +#if defined(VK_EXT_pageable_device_local_memory) + PFN_vkSetDeviceMemoryPriorityEXT vkSetDeviceMemoryPriorityEXT; +#endif /* defined(VK_EXT_pageable_device_local_memory) */ +#if defined(VK_EXT_pipeline_properties) + PFN_vkGetPipelinePropertiesEXT vkGetPipelinePropertiesEXT; +#endif /* defined(VK_EXT_pipeline_properties) */ +#if defined(VK_EXT_private_data) + PFN_vkCreatePrivateDataSlotEXT vkCreatePrivateDataSlotEXT; + PFN_vkDestroyPrivateDataSlotEXT vkDestroyPrivateDataSlotEXT; + PFN_vkGetPrivateDataEXT vkGetPrivateDataEXT; + PFN_vkSetPrivateDataEXT vkSetPrivateDataEXT; +#endif /* defined(VK_EXT_private_data) */ +#if defined(VK_EXT_sample_locations) + PFN_vkCmdSetSampleLocationsEXT vkCmdSetSampleLocationsEXT; +#endif /* defined(VK_EXT_sample_locations) */ +#if defined(VK_EXT_shader_module_identifier) + PFN_vkGetShaderModuleCreateInfoIdentifierEXT vkGetShaderModuleCreateInfoIdentifierEXT; + PFN_vkGetShaderModuleIdentifierEXT vkGetShaderModuleIdentifierEXT; +#endif /* defined(VK_EXT_shader_module_identifier) */ +#if defined(VK_EXT_shader_object) + PFN_vkCmdBindShadersEXT vkCmdBindShadersEXT; + PFN_vkCreateShadersEXT vkCreateShadersEXT; + PFN_vkDestroyShaderEXT vkDestroyShaderEXT; + PFN_vkGetShaderBinaryDataEXT vkGetShaderBinaryDataEXT; +#endif /* defined(VK_EXT_shader_object) */ +#if defined(VK_EXT_swapchain_maintenance1) + PFN_vkReleaseSwapchainImagesEXT vkReleaseSwapchainImagesEXT; +#endif /* defined(VK_EXT_swapchain_maintenance1) */ +#if defined(VK_EXT_transform_feedback) + PFN_vkCmdBeginQueryIndexedEXT vkCmdBeginQueryIndexedEXT; + PFN_vkCmdBeginTransformFeedbackEXT vkCmdBeginTransformFeedbackEXT; + PFN_vkCmdBindTransformFeedbackBuffersEXT vkCmdBindTransformFeedbackBuffersEXT; + PFN_vkCmdDrawIndirectByteCountEXT vkCmdDrawIndirectByteCountEXT; + PFN_vkCmdEndQueryIndexedEXT vkCmdEndQueryIndexedEXT; + PFN_vkCmdEndTransformFeedbackEXT vkCmdEndTransformFeedbackEXT; +#endif /* defined(VK_EXT_transform_feedback) */ +#if defined(VK_EXT_validation_cache) + PFN_vkCreateValidationCacheEXT vkCreateValidationCacheEXT; + PFN_vkDestroyValidationCacheEXT vkDestroyValidationCacheEXT; + PFN_vkGetValidationCacheDataEXT vkGetValidationCacheDataEXT; + PFN_vkMergeValidationCachesEXT vkMergeValidationCachesEXT; +#endif /* defined(VK_EXT_validation_cache) */ +#if defined(VK_FUCHSIA_buffer_collection) + PFN_vkCreateBufferCollectionFUCHSIA vkCreateBufferCollectionFUCHSIA; + PFN_vkDestroyBufferCollectionFUCHSIA vkDestroyBufferCollectionFUCHSIA; + PFN_vkGetBufferCollectionPropertiesFUCHSIA vkGetBufferCollectionPropertiesFUCHSIA; + PFN_vkSetBufferCollectionBufferConstraintsFUCHSIA vkSetBufferCollectionBufferConstraintsFUCHSIA; + PFN_vkSetBufferCollectionImageConstraintsFUCHSIA vkSetBufferCollectionImageConstraintsFUCHSIA; +#endif /* defined(VK_FUCHSIA_buffer_collection) */ +#if defined(VK_FUCHSIA_external_memory) + PFN_vkGetMemoryZirconHandleFUCHSIA vkGetMemoryZirconHandleFUCHSIA; + PFN_vkGetMemoryZirconHandlePropertiesFUCHSIA vkGetMemoryZirconHandlePropertiesFUCHSIA; +#endif /* defined(VK_FUCHSIA_external_memory) */ +#if defined(VK_FUCHSIA_external_semaphore) + PFN_vkGetSemaphoreZirconHandleFUCHSIA vkGetSemaphoreZirconHandleFUCHSIA; + PFN_vkImportSemaphoreZirconHandleFUCHSIA vkImportSemaphoreZirconHandleFUCHSIA; +#endif /* defined(VK_FUCHSIA_external_semaphore) */ +#if defined(VK_GOOGLE_display_timing) + PFN_vkGetPastPresentationTimingGOOGLE vkGetPastPresentationTimingGOOGLE; + PFN_vkGetRefreshCycleDurationGOOGLE vkGetRefreshCycleDurationGOOGLE; +#endif /* defined(VK_GOOGLE_display_timing) */ +#if defined(VK_HUAWEI_cluster_culling_shader) + PFN_vkCmdDrawClusterHUAWEI vkCmdDrawClusterHUAWEI; + PFN_vkCmdDrawClusterIndirectHUAWEI vkCmdDrawClusterIndirectHUAWEI; +#endif /* defined(VK_HUAWEI_cluster_culling_shader) */ +#if defined(VK_HUAWEI_invocation_mask) + PFN_vkCmdBindInvocationMaskHUAWEI vkCmdBindInvocationMaskHUAWEI; +#endif /* defined(VK_HUAWEI_invocation_mask) */ +#if defined(VK_HUAWEI_subpass_shading) && VK_HUAWEI_SUBPASS_SHADING_SPEC_VERSION >= 2 + PFN_vkGetDeviceSubpassShadingMaxWorkgroupSizeHUAWEI vkGetDeviceSubpassShadingMaxWorkgroupSizeHUAWEI; +#endif /* defined(VK_HUAWEI_subpass_shading) && VK_HUAWEI_SUBPASS_SHADING_SPEC_VERSION >= 2 */ +#if defined(VK_HUAWEI_subpass_shading) + PFN_vkCmdSubpassShadingHUAWEI vkCmdSubpassShadingHUAWEI; +#endif /* defined(VK_HUAWEI_subpass_shading) */ +#if defined(VK_INTEL_performance_query) + PFN_vkAcquirePerformanceConfigurationINTEL vkAcquirePerformanceConfigurationINTEL; + PFN_vkCmdSetPerformanceMarkerINTEL vkCmdSetPerformanceMarkerINTEL; + PFN_vkCmdSetPerformanceOverrideINTEL vkCmdSetPerformanceOverrideINTEL; + PFN_vkCmdSetPerformanceStreamMarkerINTEL vkCmdSetPerformanceStreamMarkerINTEL; + PFN_vkGetPerformanceParameterINTEL vkGetPerformanceParameterINTEL; + PFN_vkInitializePerformanceApiINTEL vkInitializePerformanceApiINTEL; + PFN_vkQueueSetPerformanceConfigurationINTEL vkQueueSetPerformanceConfigurationINTEL; + PFN_vkReleasePerformanceConfigurationINTEL vkReleasePerformanceConfigurationINTEL; + PFN_vkUninitializePerformanceApiINTEL vkUninitializePerformanceApiINTEL; +#endif /* defined(VK_INTEL_performance_query) */ +#if defined(VK_KHR_acceleration_structure) + PFN_vkBuildAccelerationStructuresKHR vkBuildAccelerationStructuresKHR; + PFN_vkCmdBuildAccelerationStructuresIndirectKHR vkCmdBuildAccelerationStructuresIndirectKHR; + PFN_vkCmdBuildAccelerationStructuresKHR vkCmdBuildAccelerationStructuresKHR; + PFN_vkCmdCopyAccelerationStructureKHR vkCmdCopyAccelerationStructureKHR; + PFN_vkCmdCopyAccelerationStructureToMemoryKHR vkCmdCopyAccelerationStructureToMemoryKHR; + PFN_vkCmdCopyMemoryToAccelerationStructureKHR vkCmdCopyMemoryToAccelerationStructureKHR; + PFN_vkCmdWriteAccelerationStructuresPropertiesKHR vkCmdWriteAccelerationStructuresPropertiesKHR; + PFN_vkCopyAccelerationStructureKHR vkCopyAccelerationStructureKHR; + PFN_vkCopyAccelerationStructureToMemoryKHR vkCopyAccelerationStructureToMemoryKHR; + PFN_vkCopyMemoryToAccelerationStructureKHR vkCopyMemoryToAccelerationStructureKHR; + PFN_vkCreateAccelerationStructureKHR vkCreateAccelerationStructureKHR; + PFN_vkDestroyAccelerationStructureKHR vkDestroyAccelerationStructureKHR; + PFN_vkGetAccelerationStructureBuildSizesKHR vkGetAccelerationStructureBuildSizesKHR; + PFN_vkGetAccelerationStructureDeviceAddressKHR vkGetAccelerationStructureDeviceAddressKHR; + PFN_vkGetDeviceAccelerationStructureCompatibilityKHR vkGetDeviceAccelerationStructureCompatibilityKHR; + PFN_vkWriteAccelerationStructuresPropertiesKHR vkWriteAccelerationStructuresPropertiesKHR; +#endif /* defined(VK_KHR_acceleration_structure) */ +#if defined(VK_KHR_bind_memory2) + PFN_vkBindBufferMemory2KHR vkBindBufferMemory2KHR; + PFN_vkBindImageMemory2KHR vkBindImageMemory2KHR; +#endif /* defined(VK_KHR_bind_memory2) */ +#if defined(VK_KHR_buffer_device_address) + PFN_vkGetBufferDeviceAddressKHR vkGetBufferDeviceAddressKHR; + PFN_vkGetBufferOpaqueCaptureAddressKHR vkGetBufferOpaqueCaptureAddressKHR; + PFN_vkGetDeviceMemoryOpaqueCaptureAddressKHR vkGetDeviceMemoryOpaqueCaptureAddressKHR; +#endif /* defined(VK_KHR_buffer_device_address) */ +#if defined(VK_KHR_calibrated_timestamps) + PFN_vkGetCalibratedTimestampsKHR vkGetCalibratedTimestampsKHR; +#endif /* defined(VK_KHR_calibrated_timestamps) */ +#if defined(VK_KHR_copy_commands2) + PFN_vkCmdBlitImage2KHR vkCmdBlitImage2KHR; + PFN_vkCmdCopyBuffer2KHR vkCmdCopyBuffer2KHR; + PFN_vkCmdCopyBufferToImage2KHR vkCmdCopyBufferToImage2KHR; + PFN_vkCmdCopyImage2KHR vkCmdCopyImage2KHR; + PFN_vkCmdCopyImageToBuffer2KHR vkCmdCopyImageToBuffer2KHR; + PFN_vkCmdResolveImage2KHR vkCmdResolveImage2KHR; +#endif /* defined(VK_KHR_copy_commands2) */ +#if defined(VK_KHR_create_renderpass2) + PFN_vkCmdBeginRenderPass2KHR vkCmdBeginRenderPass2KHR; + PFN_vkCmdEndRenderPass2KHR vkCmdEndRenderPass2KHR; + PFN_vkCmdNextSubpass2KHR vkCmdNextSubpass2KHR; + PFN_vkCreateRenderPass2KHR vkCreateRenderPass2KHR; +#endif /* defined(VK_KHR_create_renderpass2) */ +#if defined(VK_KHR_deferred_host_operations) + PFN_vkCreateDeferredOperationKHR vkCreateDeferredOperationKHR; + PFN_vkDeferredOperationJoinKHR vkDeferredOperationJoinKHR; + PFN_vkDestroyDeferredOperationKHR vkDestroyDeferredOperationKHR; + PFN_vkGetDeferredOperationMaxConcurrencyKHR vkGetDeferredOperationMaxConcurrencyKHR; + PFN_vkGetDeferredOperationResultKHR vkGetDeferredOperationResultKHR; +#endif /* defined(VK_KHR_deferred_host_operations) */ +#if defined(VK_KHR_descriptor_update_template) + PFN_vkCreateDescriptorUpdateTemplateKHR vkCreateDescriptorUpdateTemplateKHR; + PFN_vkDestroyDescriptorUpdateTemplateKHR vkDestroyDescriptorUpdateTemplateKHR; + PFN_vkUpdateDescriptorSetWithTemplateKHR vkUpdateDescriptorSetWithTemplateKHR; +#endif /* defined(VK_KHR_descriptor_update_template) */ +#if defined(VK_KHR_device_group) + PFN_vkCmdDispatchBaseKHR vkCmdDispatchBaseKHR; + PFN_vkCmdSetDeviceMaskKHR vkCmdSetDeviceMaskKHR; + PFN_vkGetDeviceGroupPeerMemoryFeaturesKHR vkGetDeviceGroupPeerMemoryFeaturesKHR; +#endif /* defined(VK_KHR_device_group) */ +#if defined(VK_KHR_display_swapchain) + PFN_vkCreateSharedSwapchainsKHR vkCreateSharedSwapchainsKHR; +#endif /* defined(VK_KHR_display_swapchain) */ +#if defined(VK_KHR_draw_indirect_count) + PFN_vkCmdDrawIndexedIndirectCountKHR vkCmdDrawIndexedIndirectCountKHR; + PFN_vkCmdDrawIndirectCountKHR vkCmdDrawIndirectCountKHR; +#endif /* defined(VK_KHR_draw_indirect_count) */ +#if defined(VK_KHR_dynamic_rendering) + PFN_vkCmdBeginRenderingKHR vkCmdBeginRenderingKHR; + PFN_vkCmdEndRenderingKHR vkCmdEndRenderingKHR; +#endif /* defined(VK_KHR_dynamic_rendering) */ +#if defined(VK_KHR_dynamic_rendering_local_read) + PFN_vkCmdSetRenderingAttachmentLocationsKHR vkCmdSetRenderingAttachmentLocationsKHR; + PFN_vkCmdSetRenderingInputAttachmentIndicesKHR vkCmdSetRenderingInputAttachmentIndicesKHR; +#endif /* defined(VK_KHR_dynamic_rendering_local_read) */ +#if defined(VK_KHR_external_fence_fd) + PFN_vkGetFenceFdKHR vkGetFenceFdKHR; + PFN_vkImportFenceFdKHR vkImportFenceFdKHR; +#endif /* defined(VK_KHR_external_fence_fd) */ +#if defined(VK_KHR_external_fence_win32) + PFN_vkGetFenceWin32HandleKHR vkGetFenceWin32HandleKHR; + PFN_vkImportFenceWin32HandleKHR vkImportFenceWin32HandleKHR; +#endif /* defined(VK_KHR_external_fence_win32) */ +#if defined(VK_KHR_external_memory_fd) + PFN_vkGetMemoryFdKHR vkGetMemoryFdKHR; + PFN_vkGetMemoryFdPropertiesKHR vkGetMemoryFdPropertiesKHR; +#endif /* defined(VK_KHR_external_memory_fd) */ +#if defined(VK_KHR_external_memory_win32) + PFN_vkGetMemoryWin32HandleKHR vkGetMemoryWin32HandleKHR; + PFN_vkGetMemoryWin32HandlePropertiesKHR vkGetMemoryWin32HandlePropertiesKHR; +#endif /* defined(VK_KHR_external_memory_win32) */ +#if defined(VK_KHR_external_semaphore_fd) + PFN_vkGetSemaphoreFdKHR vkGetSemaphoreFdKHR; + PFN_vkImportSemaphoreFdKHR vkImportSemaphoreFdKHR; +#endif /* defined(VK_KHR_external_semaphore_fd) */ +#if defined(VK_KHR_external_semaphore_win32) + PFN_vkGetSemaphoreWin32HandleKHR vkGetSemaphoreWin32HandleKHR; + PFN_vkImportSemaphoreWin32HandleKHR vkImportSemaphoreWin32HandleKHR; +#endif /* defined(VK_KHR_external_semaphore_win32) */ +#if defined(VK_KHR_fragment_shading_rate) + PFN_vkCmdSetFragmentShadingRateKHR vkCmdSetFragmentShadingRateKHR; +#endif /* defined(VK_KHR_fragment_shading_rate) */ +#if defined(VK_KHR_get_memory_requirements2) + PFN_vkGetBufferMemoryRequirements2KHR vkGetBufferMemoryRequirements2KHR; + PFN_vkGetImageMemoryRequirements2KHR vkGetImageMemoryRequirements2KHR; + PFN_vkGetImageSparseMemoryRequirements2KHR vkGetImageSparseMemoryRequirements2KHR; +#endif /* defined(VK_KHR_get_memory_requirements2) */ +#if defined(VK_KHR_line_rasterization) + PFN_vkCmdSetLineStippleKHR vkCmdSetLineStippleKHR; +#endif /* defined(VK_KHR_line_rasterization) */ +#if defined(VK_KHR_maintenance1) + PFN_vkTrimCommandPoolKHR vkTrimCommandPoolKHR; +#endif /* defined(VK_KHR_maintenance1) */ +#if defined(VK_KHR_maintenance3) + PFN_vkGetDescriptorSetLayoutSupportKHR vkGetDescriptorSetLayoutSupportKHR; +#endif /* defined(VK_KHR_maintenance3) */ +#if defined(VK_KHR_maintenance4) + PFN_vkGetDeviceBufferMemoryRequirementsKHR vkGetDeviceBufferMemoryRequirementsKHR; + PFN_vkGetDeviceImageMemoryRequirementsKHR vkGetDeviceImageMemoryRequirementsKHR; + PFN_vkGetDeviceImageSparseMemoryRequirementsKHR vkGetDeviceImageSparseMemoryRequirementsKHR; +#endif /* defined(VK_KHR_maintenance4) */ +#if defined(VK_KHR_maintenance5) + PFN_vkCmdBindIndexBuffer2KHR vkCmdBindIndexBuffer2KHR; + PFN_vkGetDeviceImageSubresourceLayoutKHR vkGetDeviceImageSubresourceLayoutKHR; + PFN_vkGetImageSubresourceLayout2KHR vkGetImageSubresourceLayout2KHR; + PFN_vkGetRenderingAreaGranularityKHR vkGetRenderingAreaGranularityKHR; +#endif /* defined(VK_KHR_maintenance5) */ +#if defined(VK_KHR_maintenance6) + PFN_vkCmdBindDescriptorSets2KHR vkCmdBindDescriptorSets2KHR; + PFN_vkCmdPushConstants2KHR vkCmdPushConstants2KHR; +#endif /* defined(VK_KHR_maintenance6) */ +#if defined(VK_KHR_maintenance6) && defined(VK_KHR_push_descriptor) + PFN_vkCmdPushDescriptorSet2KHR vkCmdPushDescriptorSet2KHR; + PFN_vkCmdPushDescriptorSetWithTemplate2KHR vkCmdPushDescriptorSetWithTemplate2KHR; +#endif /* defined(VK_KHR_maintenance6) && defined(VK_KHR_push_descriptor) */ +#if defined(VK_KHR_maintenance6) && defined(VK_EXT_descriptor_buffer) + PFN_vkCmdBindDescriptorBufferEmbeddedSamplers2EXT vkCmdBindDescriptorBufferEmbeddedSamplers2EXT; + PFN_vkCmdSetDescriptorBufferOffsets2EXT vkCmdSetDescriptorBufferOffsets2EXT; +#endif /* defined(VK_KHR_maintenance6) && defined(VK_EXT_descriptor_buffer) */ +#if defined(VK_KHR_map_memory2) + PFN_vkMapMemory2KHR vkMapMemory2KHR; + PFN_vkUnmapMemory2KHR vkUnmapMemory2KHR; +#endif /* defined(VK_KHR_map_memory2) */ +#if defined(VK_KHR_performance_query) + PFN_vkAcquireProfilingLockKHR vkAcquireProfilingLockKHR; + PFN_vkReleaseProfilingLockKHR vkReleaseProfilingLockKHR; +#endif /* defined(VK_KHR_performance_query) */ +#if defined(VK_KHR_pipeline_binary) + PFN_vkCreatePipelineBinariesKHR vkCreatePipelineBinariesKHR; + PFN_vkDestroyPipelineBinaryKHR vkDestroyPipelineBinaryKHR; + PFN_vkGetPipelineBinaryDataKHR vkGetPipelineBinaryDataKHR; + PFN_vkGetPipelineKeyKHR vkGetPipelineKeyKHR; + PFN_vkReleaseCapturedPipelineDataKHR vkReleaseCapturedPipelineDataKHR; +#endif /* defined(VK_KHR_pipeline_binary) */ +#if defined(VK_KHR_pipeline_executable_properties) + PFN_vkGetPipelineExecutableInternalRepresentationsKHR vkGetPipelineExecutableInternalRepresentationsKHR; + PFN_vkGetPipelineExecutablePropertiesKHR vkGetPipelineExecutablePropertiesKHR; + PFN_vkGetPipelineExecutableStatisticsKHR vkGetPipelineExecutableStatisticsKHR; +#endif /* defined(VK_KHR_pipeline_executable_properties) */ +#if defined(VK_KHR_present_wait) + PFN_vkWaitForPresentKHR vkWaitForPresentKHR; +#endif /* defined(VK_KHR_present_wait) */ +#if defined(VK_KHR_push_descriptor) + PFN_vkCmdPushDescriptorSetKHR vkCmdPushDescriptorSetKHR; +#endif /* defined(VK_KHR_push_descriptor) */ +#if defined(VK_KHR_ray_tracing_maintenance1) && defined(VK_KHR_ray_tracing_pipeline) + PFN_vkCmdTraceRaysIndirect2KHR vkCmdTraceRaysIndirect2KHR; +#endif /* defined(VK_KHR_ray_tracing_maintenance1) && defined(VK_KHR_ray_tracing_pipeline) */ +#if defined(VK_KHR_ray_tracing_pipeline) + PFN_vkCmdSetRayTracingPipelineStackSizeKHR vkCmdSetRayTracingPipelineStackSizeKHR; + PFN_vkCmdTraceRaysIndirectKHR vkCmdTraceRaysIndirectKHR; + PFN_vkCmdTraceRaysKHR vkCmdTraceRaysKHR; + PFN_vkCreateRayTracingPipelinesKHR vkCreateRayTracingPipelinesKHR; + PFN_vkGetRayTracingCaptureReplayShaderGroupHandlesKHR vkGetRayTracingCaptureReplayShaderGroupHandlesKHR; + PFN_vkGetRayTracingShaderGroupHandlesKHR vkGetRayTracingShaderGroupHandlesKHR; + PFN_vkGetRayTracingShaderGroupStackSizeKHR vkGetRayTracingShaderGroupStackSizeKHR; +#endif /* defined(VK_KHR_ray_tracing_pipeline) */ +#if defined(VK_KHR_sampler_ycbcr_conversion) + PFN_vkCreateSamplerYcbcrConversionKHR vkCreateSamplerYcbcrConversionKHR; + PFN_vkDestroySamplerYcbcrConversionKHR vkDestroySamplerYcbcrConversionKHR; +#endif /* defined(VK_KHR_sampler_ycbcr_conversion) */ +#if defined(VK_KHR_shared_presentable_image) + PFN_vkGetSwapchainStatusKHR vkGetSwapchainStatusKHR; +#endif /* defined(VK_KHR_shared_presentable_image) */ +#if defined(VK_KHR_swapchain) + PFN_vkAcquireNextImageKHR vkAcquireNextImageKHR; + PFN_vkCreateSwapchainKHR vkCreateSwapchainKHR; + PFN_vkDestroySwapchainKHR vkDestroySwapchainKHR; + PFN_vkGetSwapchainImagesKHR vkGetSwapchainImagesKHR; + PFN_vkQueuePresentKHR vkQueuePresentKHR; +#endif /* defined(VK_KHR_swapchain) */ +#if defined(VK_KHR_synchronization2) + PFN_vkCmdPipelineBarrier2KHR vkCmdPipelineBarrier2KHR; + PFN_vkCmdResetEvent2KHR vkCmdResetEvent2KHR; + PFN_vkCmdSetEvent2KHR vkCmdSetEvent2KHR; + PFN_vkCmdWaitEvents2KHR vkCmdWaitEvents2KHR; + PFN_vkCmdWriteTimestamp2KHR vkCmdWriteTimestamp2KHR; + PFN_vkQueueSubmit2KHR vkQueueSubmit2KHR; +#endif /* defined(VK_KHR_synchronization2) */ +#if defined(VK_KHR_timeline_semaphore) + PFN_vkGetSemaphoreCounterValueKHR vkGetSemaphoreCounterValueKHR; + PFN_vkSignalSemaphoreKHR vkSignalSemaphoreKHR; + PFN_vkWaitSemaphoresKHR vkWaitSemaphoresKHR; +#endif /* defined(VK_KHR_timeline_semaphore) */ +#if defined(VK_KHR_video_decode_queue) + PFN_vkCmdDecodeVideoKHR vkCmdDecodeVideoKHR; +#endif /* defined(VK_KHR_video_decode_queue) */ +#if defined(VK_KHR_video_encode_queue) + PFN_vkCmdEncodeVideoKHR vkCmdEncodeVideoKHR; + PFN_vkGetEncodedVideoSessionParametersKHR vkGetEncodedVideoSessionParametersKHR; +#endif /* defined(VK_KHR_video_encode_queue) */ +#if defined(VK_KHR_video_queue) + PFN_vkBindVideoSessionMemoryKHR vkBindVideoSessionMemoryKHR; + PFN_vkCmdBeginVideoCodingKHR vkCmdBeginVideoCodingKHR; + PFN_vkCmdControlVideoCodingKHR vkCmdControlVideoCodingKHR; + PFN_vkCmdEndVideoCodingKHR vkCmdEndVideoCodingKHR; + PFN_vkCreateVideoSessionKHR vkCreateVideoSessionKHR; + PFN_vkCreateVideoSessionParametersKHR vkCreateVideoSessionParametersKHR; + PFN_vkDestroyVideoSessionKHR vkDestroyVideoSessionKHR; + PFN_vkDestroyVideoSessionParametersKHR vkDestroyVideoSessionParametersKHR; + PFN_vkGetVideoSessionMemoryRequirementsKHR vkGetVideoSessionMemoryRequirementsKHR; + PFN_vkUpdateVideoSessionParametersKHR vkUpdateVideoSessionParametersKHR; +#endif /* defined(VK_KHR_video_queue) */ +#if defined(VK_NVX_binary_import) + PFN_vkCmdCuLaunchKernelNVX vkCmdCuLaunchKernelNVX; + PFN_vkCreateCuFunctionNVX vkCreateCuFunctionNVX; + PFN_vkCreateCuModuleNVX vkCreateCuModuleNVX; + PFN_vkDestroyCuFunctionNVX vkDestroyCuFunctionNVX; + PFN_vkDestroyCuModuleNVX vkDestroyCuModuleNVX; +#endif /* defined(VK_NVX_binary_import) */ +#if defined(VK_NVX_image_view_handle) + PFN_vkGetImageViewHandleNVX vkGetImageViewHandleNVX; +#endif /* defined(VK_NVX_image_view_handle) */ +#if defined(VK_NVX_image_view_handle) && VK_NVX_IMAGE_VIEW_HANDLE_SPEC_VERSION >= 3 + PFN_vkGetImageViewHandle64NVX vkGetImageViewHandle64NVX; +#endif /* defined(VK_NVX_image_view_handle) && VK_NVX_IMAGE_VIEW_HANDLE_SPEC_VERSION >= 3 */ +#if defined(VK_NVX_image_view_handle) && VK_NVX_IMAGE_VIEW_HANDLE_SPEC_VERSION >= 2 + PFN_vkGetImageViewAddressNVX vkGetImageViewAddressNVX; +#endif /* defined(VK_NVX_image_view_handle) && VK_NVX_IMAGE_VIEW_HANDLE_SPEC_VERSION >= 2 */ +#if defined(VK_NV_clip_space_w_scaling) + PFN_vkCmdSetViewportWScalingNV vkCmdSetViewportWScalingNV; +#endif /* defined(VK_NV_clip_space_w_scaling) */ +#if defined(VK_NV_copy_memory_indirect) + PFN_vkCmdCopyMemoryIndirectNV vkCmdCopyMemoryIndirectNV; + PFN_vkCmdCopyMemoryToImageIndirectNV vkCmdCopyMemoryToImageIndirectNV; +#endif /* defined(VK_NV_copy_memory_indirect) */ +#if defined(VK_NV_cuda_kernel_launch) + PFN_vkCmdCudaLaunchKernelNV vkCmdCudaLaunchKernelNV; + PFN_vkCreateCudaFunctionNV vkCreateCudaFunctionNV; + PFN_vkCreateCudaModuleNV vkCreateCudaModuleNV; + PFN_vkDestroyCudaFunctionNV vkDestroyCudaFunctionNV; + PFN_vkDestroyCudaModuleNV vkDestroyCudaModuleNV; + PFN_vkGetCudaModuleCacheNV vkGetCudaModuleCacheNV; +#endif /* defined(VK_NV_cuda_kernel_launch) */ +#if defined(VK_NV_device_diagnostic_checkpoints) + PFN_vkCmdSetCheckpointNV vkCmdSetCheckpointNV; + PFN_vkGetQueueCheckpointDataNV vkGetQueueCheckpointDataNV; +#endif /* defined(VK_NV_device_diagnostic_checkpoints) */ +#if defined(VK_NV_device_diagnostic_checkpoints) && (defined(VK_VERSION_1_3) || defined(VK_KHR_synchronization2)) + PFN_vkGetQueueCheckpointData2NV vkGetQueueCheckpointData2NV; +#endif /* defined(VK_NV_device_diagnostic_checkpoints) && (defined(VK_VERSION_1_3) || defined(VK_KHR_synchronization2)) */ +#if defined(VK_NV_device_generated_commands) + PFN_vkCmdBindPipelineShaderGroupNV vkCmdBindPipelineShaderGroupNV; + PFN_vkCmdExecuteGeneratedCommandsNV vkCmdExecuteGeneratedCommandsNV; + PFN_vkCmdPreprocessGeneratedCommandsNV vkCmdPreprocessGeneratedCommandsNV; + PFN_vkCreateIndirectCommandsLayoutNV vkCreateIndirectCommandsLayoutNV; + PFN_vkDestroyIndirectCommandsLayoutNV vkDestroyIndirectCommandsLayoutNV; + PFN_vkGetGeneratedCommandsMemoryRequirementsNV vkGetGeneratedCommandsMemoryRequirementsNV; +#endif /* defined(VK_NV_device_generated_commands) */ +#if defined(VK_NV_device_generated_commands_compute) + PFN_vkCmdUpdatePipelineIndirectBufferNV vkCmdUpdatePipelineIndirectBufferNV; + PFN_vkGetPipelineIndirectDeviceAddressNV vkGetPipelineIndirectDeviceAddressNV; + PFN_vkGetPipelineIndirectMemoryRequirementsNV vkGetPipelineIndirectMemoryRequirementsNV; +#endif /* defined(VK_NV_device_generated_commands_compute) */ +#if defined(VK_NV_external_memory_rdma) + PFN_vkGetMemoryRemoteAddressNV vkGetMemoryRemoteAddressNV; +#endif /* defined(VK_NV_external_memory_rdma) */ +#if defined(VK_NV_external_memory_win32) + PFN_vkGetMemoryWin32HandleNV vkGetMemoryWin32HandleNV; +#endif /* defined(VK_NV_external_memory_win32) */ +#if defined(VK_NV_fragment_shading_rate_enums) + PFN_vkCmdSetFragmentShadingRateEnumNV vkCmdSetFragmentShadingRateEnumNV; +#endif /* defined(VK_NV_fragment_shading_rate_enums) */ +#if defined(VK_NV_low_latency2) + PFN_vkGetLatencyTimingsNV vkGetLatencyTimingsNV; + PFN_vkLatencySleepNV vkLatencySleepNV; + PFN_vkQueueNotifyOutOfBandNV vkQueueNotifyOutOfBandNV; + PFN_vkSetLatencyMarkerNV vkSetLatencyMarkerNV; + PFN_vkSetLatencySleepModeNV vkSetLatencySleepModeNV; +#endif /* defined(VK_NV_low_latency2) */ +#if defined(VK_NV_memory_decompression) + PFN_vkCmdDecompressMemoryIndirectCountNV vkCmdDecompressMemoryIndirectCountNV; + PFN_vkCmdDecompressMemoryNV vkCmdDecompressMemoryNV; +#endif /* defined(VK_NV_memory_decompression) */ +#if defined(VK_NV_mesh_shader) + PFN_vkCmdDrawMeshTasksIndirectNV vkCmdDrawMeshTasksIndirectNV; + PFN_vkCmdDrawMeshTasksNV vkCmdDrawMeshTasksNV; +#endif /* defined(VK_NV_mesh_shader) */ +#if defined(VK_NV_mesh_shader) && (defined(VK_KHR_draw_indirect_count) || defined(VK_VERSION_1_2)) + PFN_vkCmdDrawMeshTasksIndirectCountNV vkCmdDrawMeshTasksIndirectCountNV; +#endif /* defined(VK_NV_mesh_shader) && (defined(VK_KHR_draw_indirect_count) || defined(VK_VERSION_1_2)) */ +#if defined(VK_NV_optical_flow) + PFN_vkBindOpticalFlowSessionImageNV vkBindOpticalFlowSessionImageNV; + PFN_vkCmdOpticalFlowExecuteNV vkCmdOpticalFlowExecuteNV; + PFN_vkCreateOpticalFlowSessionNV vkCreateOpticalFlowSessionNV; + PFN_vkDestroyOpticalFlowSessionNV vkDestroyOpticalFlowSessionNV; +#endif /* defined(VK_NV_optical_flow) */ +#if defined(VK_NV_ray_tracing) + PFN_vkBindAccelerationStructureMemoryNV vkBindAccelerationStructureMemoryNV; + PFN_vkCmdBuildAccelerationStructureNV vkCmdBuildAccelerationStructureNV; + PFN_vkCmdCopyAccelerationStructureNV vkCmdCopyAccelerationStructureNV; + PFN_vkCmdTraceRaysNV vkCmdTraceRaysNV; + PFN_vkCmdWriteAccelerationStructuresPropertiesNV vkCmdWriteAccelerationStructuresPropertiesNV; + PFN_vkCompileDeferredNV vkCompileDeferredNV; + PFN_vkCreateAccelerationStructureNV vkCreateAccelerationStructureNV; + PFN_vkCreateRayTracingPipelinesNV vkCreateRayTracingPipelinesNV; + PFN_vkDestroyAccelerationStructureNV vkDestroyAccelerationStructureNV; + PFN_vkGetAccelerationStructureHandleNV vkGetAccelerationStructureHandleNV; + PFN_vkGetAccelerationStructureMemoryRequirementsNV vkGetAccelerationStructureMemoryRequirementsNV; + PFN_vkGetRayTracingShaderGroupHandlesNV vkGetRayTracingShaderGroupHandlesNV; +#endif /* defined(VK_NV_ray_tracing) */ +#if defined(VK_NV_scissor_exclusive) && VK_NV_SCISSOR_EXCLUSIVE_SPEC_VERSION >= 2 + PFN_vkCmdSetExclusiveScissorEnableNV vkCmdSetExclusiveScissorEnableNV; +#endif /* defined(VK_NV_scissor_exclusive) && VK_NV_SCISSOR_EXCLUSIVE_SPEC_VERSION >= 2 */ +#if defined(VK_NV_scissor_exclusive) + PFN_vkCmdSetExclusiveScissorNV vkCmdSetExclusiveScissorNV; +#endif /* defined(VK_NV_scissor_exclusive) */ +#if defined(VK_NV_shading_rate_image) + PFN_vkCmdBindShadingRateImageNV vkCmdBindShadingRateImageNV; + PFN_vkCmdSetCoarseSampleOrderNV vkCmdSetCoarseSampleOrderNV; + PFN_vkCmdSetViewportShadingRatePaletteNV vkCmdSetViewportShadingRatePaletteNV; +#endif /* defined(VK_NV_shading_rate_image) */ +#if defined(VK_QCOM_tile_properties) + PFN_vkGetDynamicRenderingTilePropertiesQCOM vkGetDynamicRenderingTilePropertiesQCOM; + PFN_vkGetFramebufferTilePropertiesQCOM vkGetFramebufferTilePropertiesQCOM; +#endif /* defined(VK_QCOM_tile_properties) */ +#if defined(VK_QNX_external_memory_screen_buffer) + PFN_vkGetScreenBufferPropertiesQNX vkGetScreenBufferPropertiesQNX; +#endif /* defined(VK_QNX_external_memory_screen_buffer) */ +#if defined(VK_VALVE_descriptor_set_host_mapping) + PFN_vkGetDescriptorSetHostMappingVALVE vkGetDescriptorSetHostMappingVALVE; + PFN_vkGetDescriptorSetLayoutHostMappingInfoVALVE vkGetDescriptorSetLayoutHostMappingInfoVALVE; +#endif /* defined(VK_VALVE_descriptor_set_host_mapping) */ +#if (defined(VK_EXT_depth_clamp_control)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_depth_clamp_control)) + PFN_vkCmdSetDepthClampRangeEXT vkCmdSetDepthClampRangeEXT; +#endif /* (defined(VK_EXT_depth_clamp_control)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_depth_clamp_control)) */ +#if (defined(VK_EXT_extended_dynamic_state)) || (defined(VK_EXT_shader_object)) + PFN_vkCmdBindVertexBuffers2EXT vkCmdBindVertexBuffers2EXT; + PFN_vkCmdSetCullModeEXT vkCmdSetCullModeEXT; + PFN_vkCmdSetDepthBoundsTestEnableEXT vkCmdSetDepthBoundsTestEnableEXT; + PFN_vkCmdSetDepthCompareOpEXT vkCmdSetDepthCompareOpEXT; + PFN_vkCmdSetDepthTestEnableEXT vkCmdSetDepthTestEnableEXT; + PFN_vkCmdSetDepthWriteEnableEXT vkCmdSetDepthWriteEnableEXT; + PFN_vkCmdSetFrontFaceEXT vkCmdSetFrontFaceEXT; + PFN_vkCmdSetPrimitiveTopologyEXT vkCmdSetPrimitiveTopologyEXT; + PFN_vkCmdSetScissorWithCountEXT vkCmdSetScissorWithCountEXT; + PFN_vkCmdSetStencilOpEXT vkCmdSetStencilOpEXT; + PFN_vkCmdSetStencilTestEnableEXT vkCmdSetStencilTestEnableEXT; + PFN_vkCmdSetViewportWithCountEXT vkCmdSetViewportWithCountEXT; +#endif /* (defined(VK_EXT_extended_dynamic_state)) || (defined(VK_EXT_shader_object)) */ +#if (defined(VK_EXT_extended_dynamic_state2)) || (defined(VK_EXT_shader_object)) + PFN_vkCmdSetDepthBiasEnableEXT vkCmdSetDepthBiasEnableEXT; + PFN_vkCmdSetLogicOpEXT vkCmdSetLogicOpEXT; + PFN_vkCmdSetPatchControlPointsEXT vkCmdSetPatchControlPointsEXT; + PFN_vkCmdSetPrimitiveRestartEnableEXT vkCmdSetPrimitiveRestartEnableEXT; + PFN_vkCmdSetRasterizerDiscardEnableEXT vkCmdSetRasterizerDiscardEnableEXT; +#endif /* (defined(VK_EXT_extended_dynamic_state2)) || (defined(VK_EXT_shader_object)) */ +#if (defined(VK_EXT_extended_dynamic_state3)) || (defined(VK_EXT_shader_object)) + PFN_vkCmdSetAlphaToCoverageEnableEXT vkCmdSetAlphaToCoverageEnableEXT; + PFN_vkCmdSetAlphaToOneEnableEXT vkCmdSetAlphaToOneEnableEXT; + PFN_vkCmdSetColorBlendEnableEXT vkCmdSetColorBlendEnableEXT; + PFN_vkCmdSetColorBlendEquationEXT vkCmdSetColorBlendEquationEXT; + PFN_vkCmdSetColorWriteMaskEXT vkCmdSetColorWriteMaskEXT; + PFN_vkCmdSetDepthClampEnableEXT vkCmdSetDepthClampEnableEXT; + PFN_vkCmdSetLogicOpEnableEXT vkCmdSetLogicOpEnableEXT; + PFN_vkCmdSetPolygonModeEXT vkCmdSetPolygonModeEXT; + PFN_vkCmdSetRasterizationSamplesEXT vkCmdSetRasterizationSamplesEXT; + PFN_vkCmdSetSampleMaskEXT vkCmdSetSampleMaskEXT; +#endif /* (defined(VK_EXT_extended_dynamic_state3)) || (defined(VK_EXT_shader_object)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && (defined(VK_KHR_maintenance2) || defined(VK_VERSION_1_1))) || (defined(VK_EXT_shader_object)) + PFN_vkCmdSetTessellationDomainOriginEXT vkCmdSetTessellationDomainOriginEXT; +#endif /* (defined(VK_EXT_extended_dynamic_state3) && (defined(VK_KHR_maintenance2) || defined(VK_VERSION_1_1))) || (defined(VK_EXT_shader_object)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_transform_feedback)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_transform_feedback)) + PFN_vkCmdSetRasterizationStreamEXT vkCmdSetRasterizationStreamEXT; +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_transform_feedback)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_transform_feedback)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_conservative_rasterization)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_conservative_rasterization)) + PFN_vkCmdSetConservativeRasterizationModeEXT vkCmdSetConservativeRasterizationModeEXT; + PFN_vkCmdSetExtraPrimitiveOverestimationSizeEXT vkCmdSetExtraPrimitiveOverestimationSizeEXT; +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_conservative_rasterization)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_conservative_rasterization)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_depth_clip_enable)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_depth_clip_enable)) + PFN_vkCmdSetDepthClipEnableEXT vkCmdSetDepthClipEnableEXT; +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_depth_clip_enable)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_depth_clip_enable)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_sample_locations)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_sample_locations)) + PFN_vkCmdSetSampleLocationsEnableEXT vkCmdSetSampleLocationsEnableEXT; +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_sample_locations)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_sample_locations)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_blend_operation_advanced)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_blend_operation_advanced)) + PFN_vkCmdSetColorBlendAdvancedEXT vkCmdSetColorBlendAdvancedEXT; +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_blend_operation_advanced)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_blend_operation_advanced)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_provoking_vertex)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_provoking_vertex)) + PFN_vkCmdSetProvokingVertexModeEXT vkCmdSetProvokingVertexModeEXT; +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_provoking_vertex)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_provoking_vertex)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_line_rasterization)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_line_rasterization)) + PFN_vkCmdSetLineRasterizationModeEXT vkCmdSetLineRasterizationModeEXT; + PFN_vkCmdSetLineStippleEnableEXT vkCmdSetLineStippleEnableEXT; +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_line_rasterization)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_line_rasterization)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_depth_clip_control)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_depth_clip_control)) + PFN_vkCmdSetDepthClipNegativeOneToOneEXT vkCmdSetDepthClipNegativeOneToOneEXT; +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_depth_clip_control)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_depth_clip_control)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_clip_space_w_scaling)) || (defined(VK_EXT_shader_object) && defined(VK_NV_clip_space_w_scaling)) + PFN_vkCmdSetViewportWScalingEnableNV vkCmdSetViewportWScalingEnableNV; +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_clip_space_w_scaling)) || (defined(VK_EXT_shader_object) && defined(VK_NV_clip_space_w_scaling)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_viewport_swizzle)) || (defined(VK_EXT_shader_object) && defined(VK_NV_viewport_swizzle)) + PFN_vkCmdSetViewportSwizzleNV vkCmdSetViewportSwizzleNV; +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_viewport_swizzle)) || (defined(VK_EXT_shader_object) && defined(VK_NV_viewport_swizzle)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_fragment_coverage_to_color)) || (defined(VK_EXT_shader_object) && defined(VK_NV_fragment_coverage_to_color)) + PFN_vkCmdSetCoverageToColorEnableNV vkCmdSetCoverageToColorEnableNV; + PFN_vkCmdSetCoverageToColorLocationNV vkCmdSetCoverageToColorLocationNV; +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_fragment_coverage_to_color)) || (defined(VK_EXT_shader_object) && defined(VK_NV_fragment_coverage_to_color)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_framebuffer_mixed_samples)) || (defined(VK_EXT_shader_object) && defined(VK_NV_framebuffer_mixed_samples)) + PFN_vkCmdSetCoverageModulationModeNV vkCmdSetCoverageModulationModeNV; + PFN_vkCmdSetCoverageModulationTableEnableNV vkCmdSetCoverageModulationTableEnableNV; + PFN_vkCmdSetCoverageModulationTableNV vkCmdSetCoverageModulationTableNV; +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_framebuffer_mixed_samples)) || (defined(VK_EXT_shader_object) && defined(VK_NV_framebuffer_mixed_samples)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_shading_rate_image)) || (defined(VK_EXT_shader_object) && defined(VK_NV_shading_rate_image)) + PFN_vkCmdSetShadingRateImageEnableNV vkCmdSetShadingRateImageEnableNV; +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_shading_rate_image)) || (defined(VK_EXT_shader_object) && defined(VK_NV_shading_rate_image)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_representative_fragment_test)) || (defined(VK_EXT_shader_object) && defined(VK_NV_representative_fragment_test)) + PFN_vkCmdSetRepresentativeFragmentTestEnableNV vkCmdSetRepresentativeFragmentTestEnableNV; +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_representative_fragment_test)) || (defined(VK_EXT_shader_object) && defined(VK_NV_representative_fragment_test)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_coverage_reduction_mode)) || (defined(VK_EXT_shader_object) && defined(VK_NV_coverage_reduction_mode)) + PFN_vkCmdSetCoverageReductionModeNV vkCmdSetCoverageReductionModeNV; +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_coverage_reduction_mode)) || (defined(VK_EXT_shader_object) && defined(VK_NV_coverage_reduction_mode)) */ +#if (defined(VK_EXT_host_image_copy)) || (defined(VK_EXT_image_compression_control)) + PFN_vkGetImageSubresourceLayout2EXT vkGetImageSubresourceLayout2EXT; +#endif /* (defined(VK_EXT_host_image_copy)) || (defined(VK_EXT_image_compression_control)) */ +#if (defined(VK_EXT_shader_object)) || (defined(VK_EXT_vertex_input_dynamic_state)) + PFN_vkCmdSetVertexInputEXT vkCmdSetVertexInputEXT; +#endif /* (defined(VK_EXT_shader_object)) || (defined(VK_EXT_vertex_input_dynamic_state)) */ +#if (defined(VK_KHR_descriptor_update_template) && defined(VK_KHR_push_descriptor)) || (defined(VK_KHR_push_descriptor) && (defined(VK_VERSION_1_1) || defined(VK_KHR_descriptor_update_template))) + PFN_vkCmdPushDescriptorSetWithTemplateKHR vkCmdPushDescriptorSetWithTemplateKHR; +#endif /* (defined(VK_KHR_descriptor_update_template) && defined(VK_KHR_push_descriptor)) || (defined(VK_KHR_push_descriptor) && (defined(VK_VERSION_1_1) || defined(VK_KHR_descriptor_update_template))) */ +#if (defined(VK_KHR_device_group) && defined(VK_KHR_surface)) || (defined(VK_KHR_swapchain) && defined(VK_VERSION_1_1)) + PFN_vkGetDeviceGroupPresentCapabilitiesKHR vkGetDeviceGroupPresentCapabilitiesKHR; + PFN_vkGetDeviceGroupSurfacePresentModesKHR vkGetDeviceGroupSurfacePresentModesKHR; +#endif /* (defined(VK_KHR_device_group) && defined(VK_KHR_surface)) || (defined(VK_KHR_swapchain) && defined(VK_VERSION_1_1)) */ +#if (defined(VK_KHR_device_group) && defined(VK_KHR_swapchain)) || (defined(VK_KHR_swapchain) && defined(VK_VERSION_1_1)) + PFN_vkAcquireNextImage2KHR vkAcquireNextImage2KHR; +#endif /* (defined(VK_KHR_device_group) && defined(VK_KHR_swapchain)) || (defined(VK_KHR_swapchain) && defined(VK_VERSION_1_1)) */ + /* VOLK_GENERATE_DEVICE_TABLE */ +}; + +/* VOLK_GENERATE_PROTOTYPES_H */ +#if defined(VK_VERSION_1_0) +extern PFN_vkAllocateCommandBuffers vkAllocateCommandBuffers; +extern PFN_vkAllocateDescriptorSets vkAllocateDescriptorSets; +extern PFN_vkAllocateMemory vkAllocateMemory; +extern PFN_vkBeginCommandBuffer vkBeginCommandBuffer; +extern PFN_vkBindBufferMemory vkBindBufferMemory; +extern PFN_vkBindImageMemory vkBindImageMemory; +extern PFN_vkCmdBeginQuery vkCmdBeginQuery; +extern PFN_vkCmdBeginRenderPass vkCmdBeginRenderPass; +extern PFN_vkCmdBindDescriptorSets vkCmdBindDescriptorSets; +extern PFN_vkCmdBindIndexBuffer vkCmdBindIndexBuffer; +extern PFN_vkCmdBindPipeline vkCmdBindPipeline; +extern PFN_vkCmdBindVertexBuffers vkCmdBindVertexBuffers; +extern PFN_vkCmdBlitImage vkCmdBlitImage; +extern PFN_vkCmdClearAttachments vkCmdClearAttachments; +extern PFN_vkCmdClearColorImage vkCmdClearColorImage; +extern PFN_vkCmdClearDepthStencilImage vkCmdClearDepthStencilImage; +extern PFN_vkCmdCopyBuffer vkCmdCopyBuffer; +extern PFN_vkCmdCopyBufferToImage vkCmdCopyBufferToImage; +extern PFN_vkCmdCopyImage vkCmdCopyImage; +extern PFN_vkCmdCopyImageToBuffer vkCmdCopyImageToBuffer; +extern PFN_vkCmdCopyQueryPoolResults vkCmdCopyQueryPoolResults; +extern PFN_vkCmdDispatch vkCmdDispatch; +extern PFN_vkCmdDispatchIndirect vkCmdDispatchIndirect; +extern PFN_vkCmdDraw vkCmdDraw; +extern PFN_vkCmdDrawIndexed vkCmdDrawIndexed; +extern PFN_vkCmdDrawIndexedIndirect vkCmdDrawIndexedIndirect; +extern PFN_vkCmdDrawIndirect vkCmdDrawIndirect; +extern PFN_vkCmdEndQuery vkCmdEndQuery; +extern PFN_vkCmdEndRenderPass vkCmdEndRenderPass; +extern PFN_vkCmdExecuteCommands vkCmdExecuteCommands; +extern PFN_vkCmdFillBuffer vkCmdFillBuffer; +extern PFN_vkCmdNextSubpass vkCmdNextSubpass; +extern PFN_vkCmdPipelineBarrier vkCmdPipelineBarrier; +extern PFN_vkCmdPushConstants vkCmdPushConstants; +extern PFN_vkCmdResetEvent vkCmdResetEvent; +extern PFN_vkCmdResetQueryPool vkCmdResetQueryPool; +extern PFN_vkCmdResolveImage vkCmdResolveImage; +extern PFN_vkCmdSetBlendConstants vkCmdSetBlendConstants; +extern PFN_vkCmdSetDepthBias vkCmdSetDepthBias; +extern PFN_vkCmdSetDepthBounds vkCmdSetDepthBounds; +extern PFN_vkCmdSetEvent vkCmdSetEvent; +extern PFN_vkCmdSetLineWidth vkCmdSetLineWidth; +extern PFN_vkCmdSetScissor vkCmdSetScissor; +extern PFN_vkCmdSetStencilCompareMask vkCmdSetStencilCompareMask; +extern PFN_vkCmdSetStencilReference vkCmdSetStencilReference; +extern PFN_vkCmdSetStencilWriteMask vkCmdSetStencilWriteMask; +extern PFN_vkCmdSetViewport vkCmdSetViewport; +extern PFN_vkCmdUpdateBuffer vkCmdUpdateBuffer; +extern PFN_vkCmdWaitEvents vkCmdWaitEvents; +extern PFN_vkCmdWriteTimestamp vkCmdWriteTimestamp; +extern PFN_vkCreateBuffer vkCreateBuffer; +extern PFN_vkCreateBufferView vkCreateBufferView; +extern PFN_vkCreateCommandPool vkCreateCommandPool; +extern PFN_vkCreateComputePipelines vkCreateComputePipelines; +extern PFN_vkCreateDescriptorPool vkCreateDescriptorPool; +extern PFN_vkCreateDescriptorSetLayout vkCreateDescriptorSetLayout; +extern PFN_vkCreateDevice vkCreateDevice; +extern PFN_vkCreateEvent vkCreateEvent; +extern PFN_vkCreateFence vkCreateFence; +extern PFN_vkCreateFramebuffer vkCreateFramebuffer; +extern PFN_vkCreateGraphicsPipelines vkCreateGraphicsPipelines; +extern PFN_vkCreateImage vkCreateImage; +extern PFN_vkCreateImageView vkCreateImageView; +extern PFN_vkCreateInstance vkCreateInstance; +extern PFN_vkCreatePipelineCache vkCreatePipelineCache; +extern PFN_vkCreatePipelineLayout vkCreatePipelineLayout; +extern PFN_vkCreateQueryPool vkCreateQueryPool; +extern PFN_vkCreateRenderPass vkCreateRenderPass; +extern PFN_vkCreateSampler vkCreateSampler; +extern PFN_vkCreateSemaphore vkCreateSemaphore; +extern PFN_vkCreateShaderModule vkCreateShaderModule; +extern PFN_vkDestroyBuffer vkDestroyBuffer; +extern PFN_vkDestroyBufferView vkDestroyBufferView; +extern PFN_vkDestroyCommandPool vkDestroyCommandPool; +extern PFN_vkDestroyDescriptorPool vkDestroyDescriptorPool; +extern PFN_vkDestroyDescriptorSetLayout vkDestroyDescriptorSetLayout; +extern PFN_vkDestroyDevice vkDestroyDevice; +extern PFN_vkDestroyEvent vkDestroyEvent; +extern PFN_vkDestroyFence vkDestroyFence; +extern PFN_vkDestroyFramebuffer vkDestroyFramebuffer; +extern PFN_vkDestroyImage vkDestroyImage; +extern PFN_vkDestroyImageView vkDestroyImageView; +extern PFN_vkDestroyInstance vkDestroyInstance; +extern PFN_vkDestroyPipeline vkDestroyPipeline; +extern PFN_vkDestroyPipelineCache vkDestroyPipelineCache; +extern PFN_vkDestroyPipelineLayout vkDestroyPipelineLayout; +extern PFN_vkDestroyQueryPool vkDestroyQueryPool; +extern PFN_vkDestroyRenderPass vkDestroyRenderPass; +extern PFN_vkDestroySampler vkDestroySampler; +extern PFN_vkDestroySemaphore vkDestroySemaphore; +extern PFN_vkDestroyShaderModule vkDestroyShaderModule; +extern PFN_vkDeviceWaitIdle vkDeviceWaitIdle; +extern PFN_vkEndCommandBuffer vkEndCommandBuffer; +extern PFN_vkEnumerateDeviceExtensionProperties vkEnumerateDeviceExtensionProperties; +extern PFN_vkEnumerateDeviceLayerProperties vkEnumerateDeviceLayerProperties; +extern PFN_vkEnumerateInstanceExtensionProperties vkEnumerateInstanceExtensionProperties; +extern PFN_vkEnumerateInstanceLayerProperties vkEnumerateInstanceLayerProperties; +extern PFN_vkEnumeratePhysicalDevices vkEnumeratePhysicalDevices; +extern PFN_vkFlushMappedMemoryRanges vkFlushMappedMemoryRanges; +extern PFN_vkFreeCommandBuffers vkFreeCommandBuffers; +extern PFN_vkFreeDescriptorSets vkFreeDescriptorSets; +extern PFN_vkFreeMemory vkFreeMemory; +extern PFN_vkGetBufferMemoryRequirements vkGetBufferMemoryRequirements; +extern PFN_vkGetDeviceMemoryCommitment vkGetDeviceMemoryCommitment; +extern PFN_vkGetDeviceProcAddr vkGetDeviceProcAddr; +extern PFN_vkGetDeviceQueue vkGetDeviceQueue; +extern PFN_vkGetEventStatus vkGetEventStatus; +extern PFN_vkGetFenceStatus vkGetFenceStatus; +extern PFN_vkGetImageMemoryRequirements vkGetImageMemoryRequirements; +extern PFN_vkGetImageSparseMemoryRequirements vkGetImageSparseMemoryRequirements; +extern PFN_vkGetImageSubresourceLayout vkGetImageSubresourceLayout; +extern PFN_vkGetInstanceProcAddr vkGetInstanceProcAddr; +extern PFN_vkGetPhysicalDeviceFeatures vkGetPhysicalDeviceFeatures; +extern PFN_vkGetPhysicalDeviceFormatProperties vkGetPhysicalDeviceFormatProperties; +extern PFN_vkGetPhysicalDeviceImageFormatProperties vkGetPhysicalDeviceImageFormatProperties; +extern PFN_vkGetPhysicalDeviceMemoryProperties vkGetPhysicalDeviceMemoryProperties; +extern PFN_vkGetPhysicalDeviceProperties vkGetPhysicalDeviceProperties; +extern PFN_vkGetPhysicalDeviceQueueFamilyProperties vkGetPhysicalDeviceQueueFamilyProperties; +extern PFN_vkGetPhysicalDeviceSparseImageFormatProperties vkGetPhysicalDeviceSparseImageFormatProperties; +extern PFN_vkGetPipelineCacheData vkGetPipelineCacheData; +extern PFN_vkGetQueryPoolResults vkGetQueryPoolResults; +extern PFN_vkGetRenderAreaGranularity vkGetRenderAreaGranularity; +extern PFN_vkInvalidateMappedMemoryRanges vkInvalidateMappedMemoryRanges; +extern PFN_vkMapMemory vkMapMemory; +extern PFN_vkMergePipelineCaches vkMergePipelineCaches; +extern PFN_vkQueueBindSparse vkQueueBindSparse; +extern PFN_vkQueueSubmit vkQueueSubmit; +extern PFN_vkQueueWaitIdle vkQueueWaitIdle; +extern PFN_vkResetCommandBuffer vkResetCommandBuffer; +extern PFN_vkResetCommandPool vkResetCommandPool; +extern PFN_vkResetDescriptorPool vkResetDescriptorPool; +extern PFN_vkResetEvent vkResetEvent; +extern PFN_vkResetFences vkResetFences; +extern PFN_vkSetEvent vkSetEvent; +extern PFN_vkUnmapMemory vkUnmapMemory; +extern PFN_vkUpdateDescriptorSets vkUpdateDescriptorSets; +extern PFN_vkWaitForFences vkWaitForFences; +#endif /* defined(VK_VERSION_1_0) */ +#if defined(VK_VERSION_1_1) +extern PFN_vkBindBufferMemory2 vkBindBufferMemory2; +extern PFN_vkBindImageMemory2 vkBindImageMemory2; +extern PFN_vkCmdDispatchBase vkCmdDispatchBase; +extern PFN_vkCmdSetDeviceMask vkCmdSetDeviceMask; +extern PFN_vkCreateDescriptorUpdateTemplate vkCreateDescriptorUpdateTemplate; +extern PFN_vkCreateSamplerYcbcrConversion vkCreateSamplerYcbcrConversion; +extern PFN_vkDestroyDescriptorUpdateTemplate vkDestroyDescriptorUpdateTemplate; +extern PFN_vkDestroySamplerYcbcrConversion vkDestroySamplerYcbcrConversion; +extern PFN_vkEnumerateInstanceVersion vkEnumerateInstanceVersion; +extern PFN_vkEnumeratePhysicalDeviceGroups vkEnumeratePhysicalDeviceGroups; +extern PFN_vkGetBufferMemoryRequirements2 vkGetBufferMemoryRequirements2; +extern PFN_vkGetDescriptorSetLayoutSupport vkGetDescriptorSetLayoutSupport; +extern PFN_vkGetDeviceGroupPeerMemoryFeatures vkGetDeviceGroupPeerMemoryFeatures; +extern PFN_vkGetDeviceQueue2 vkGetDeviceQueue2; +extern PFN_vkGetImageMemoryRequirements2 vkGetImageMemoryRequirements2; +extern PFN_vkGetImageSparseMemoryRequirements2 vkGetImageSparseMemoryRequirements2; +extern PFN_vkGetPhysicalDeviceExternalBufferProperties vkGetPhysicalDeviceExternalBufferProperties; +extern PFN_vkGetPhysicalDeviceExternalFenceProperties vkGetPhysicalDeviceExternalFenceProperties; +extern PFN_vkGetPhysicalDeviceExternalSemaphoreProperties vkGetPhysicalDeviceExternalSemaphoreProperties; +extern PFN_vkGetPhysicalDeviceFeatures2 vkGetPhysicalDeviceFeatures2; +extern PFN_vkGetPhysicalDeviceFormatProperties2 vkGetPhysicalDeviceFormatProperties2; +extern PFN_vkGetPhysicalDeviceImageFormatProperties2 vkGetPhysicalDeviceImageFormatProperties2; +extern PFN_vkGetPhysicalDeviceMemoryProperties2 vkGetPhysicalDeviceMemoryProperties2; +extern PFN_vkGetPhysicalDeviceProperties2 vkGetPhysicalDeviceProperties2; +extern PFN_vkGetPhysicalDeviceQueueFamilyProperties2 vkGetPhysicalDeviceQueueFamilyProperties2; +extern PFN_vkGetPhysicalDeviceSparseImageFormatProperties2 vkGetPhysicalDeviceSparseImageFormatProperties2; +extern PFN_vkTrimCommandPool vkTrimCommandPool; +extern PFN_vkUpdateDescriptorSetWithTemplate vkUpdateDescriptorSetWithTemplate; +#endif /* defined(VK_VERSION_1_1) */ +#if defined(VK_VERSION_1_2) +extern PFN_vkCmdBeginRenderPass2 vkCmdBeginRenderPass2; +extern PFN_vkCmdDrawIndexedIndirectCount vkCmdDrawIndexedIndirectCount; +extern PFN_vkCmdDrawIndirectCount vkCmdDrawIndirectCount; +extern PFN_vkCmdEndRenderPass2 vkCmdEndRenderPass2; +extern PFN_vkCmdNextSubpass2 vkCmdNextSubpass2; +extern PFN_vkCreateRenderPass2 vkCreateRenderPass2; +extern PFN_vkGetBufferDeviceAddress vkGetBufferDeviceAddress; +extern PFN_vkGetBufferOpaqueCaptureAddress vkGetBufferOpaqueCaptureAddress; +extern PFN_vkGetDeviceMemoryOpaqueCaptureAddress vkGetDeviceMemoryOpaqueCaptureAddress; +extern PFN_vkGetSemaphoreCounterValue vkGetSemaphoreCounterValue; +extern PFN_vkResetQueryPool vkResetQueryPool; +extern PFN_vkSignalSemaphore vkSignalSemaphore; +extern PFN_vkWaitSemaphores vkWaitSemaphores; +#endif /* defined(VK_VERSION_1_2) */ +#if defined(VK_VERSION_1_3) +extern PFN_vkCmdBeginRendering vkCmdBeginRendering; +extern PFN_vkCmdBindVertexBuffers2 vkCmdBindVertexBuffers2; +extern PFN_vkCmdBlitImage2 vkCmdBlitImage2; +extern PFN_vkCmdCopyBuffer2 vkCmdCopyBuffer2; +extern PFN_vkCmdCopyBufferToImage2 vkCmdCopyBufferToImage2; +extern PFN_vkCmdCopyImage2 vkCmdCopyImage2; +extern PFN_vkCmdCopyImageToBuffer2 vkCmdCopyImageToBuffer2; +extern PFN_vkCmdEndRendering vkCmdEndRendering; +extern PFN_vkCmdPipelineBarrier2 vkCmdPipelineBarrier2; +extern PFN_vkCmdResetEvent2 vkCmdResetEvent2; +extern PFN_vkCmdResolveImage2 vkCmdResolveImage2; +extern PFN_vkCmdSetCullMode vkCmdSetCullMode; +extern PFN_vkCmdSetDepthBiasEnable vkCmdSetDepthBiasEnable; +extern PFN_vkCmdSetDepthBoundsTestEnable vkCmdSetDepthBoundsTestEnable; +extern PFN_vkCmdSetDepthCompareOp vkCmdSetDepthCompareOp; +extern PFN_vkCmdSetDepthTestEnable vkCmdSetDepthTestEnable; +extern PFN_vkCmdSetDepthWriteEnable vkCmdSetDepthWriteEnable; +extern PFN_vkCmdSetEvent2 vkCmdSetEvent2; +extern PFN_vkCmdSetFrontFace vkCmdSetFrontFace; +extern PFN_vkCmdSetPrimitiveRestartEnable vkCmdSetPrimitiveRestartEnable; +extern PFN_vkCmdSetPrimitiveTopology vkCmdSetPrimitiveTopology; +extern PFN_vkCmdSetRasterizerDiscardEnable vkCmdSetRasterizerDiscardEnable; +extern PFN_vkCmdSetScissorWithCount vkCmdSetScissorWithCount; +extern PFN_vkCmdSetStencilOp vkCmdSetStencilOp; +extern PFN_vkCmdSetStencilTestEnable vkCmdSetStencilTestEnable; +extern PFN_vkCmdSetViewportWithCount vkCmdSetViewportWithCount; +extern PFN_vkCmdWaitEvents2 vkCmdWaitEvents2; +extern PFN_vkCmdWriteTimestamp2 vkCmdWriteTimestamp2; +extern PFN_vkCreatePrivateDataSlot vkCreatePrivateDataSlot; +extern PFN_vkDestroyPrivateDataSlot vkDestroyPrivateDataSlot; +extern PFN_vkGetDeviceBufferMemoryRequirements vkGetDeviceBufferMemoryRequirements; +extern PFN_vkGetDeviceImageMemoryRequirements vkGetDeviceImageMemoryRequirements; +extern PFN_vkGetDeviceImageSparseMemoryRequirements vkGetDeviceImageSparseMemoryRequirements; +extern PFN_vkGetPhysicalDeviceToolProperties vkGetPhysicalDeviceToolProperties; +extern PFN_vkGetPrivateData vkGetPrivateData; +extern PFN_vkQueueSubmit2 vkQueueSubmit2; +extern PFN_vkSetPrivateData vkSetPrivateData; +#endif /* defined(VK_VERSION_1_3) */ +#if defined(VK_VERSION_1_4) +extern PFN_vkCmdBindDescriptorSets2 vkCmdBindDescriptorSets2; +extern PFN_vkCmdBindIndexBuffer2 vkCmdBindIndexBuffer2; +extern PFN_vkCmdPushConstants2 vkCmdPushConstants2; +extern PFN_vkCmdPushDescriptorSet vkCmdPushDescriptorSet; +extern PFN_vkCmdPushDescriptorSet2 vkCmdPushDescriptorSet2; +extern PFN_vkCmdPushDescriptorSetWithTemplate vkCmdPushDescriptorSetWithTemplate; +extern PFN_vkCmdPushDescriptorSetWithTemplate2 vkCmdPushDescriptorSetWithTemplate2; +extern PFN_vkCmdSetLineStipple vkCmdSetLineStipple; +extern PFN_vkCmdSetRenderingAttachmentLocations vkCmdSetRenderingAttachmentLocations; +extern PFN_vkCmdSetRenderingInputAttachmentIndices vkCmdSetRenderingInputAttachmentIndices; +extern PFN_vkCopyImageToImage vkCopyImageToImage; +extern PFN_vkCopyImageToMemory vkCopyImageToMemory; +extern PFN_vkCopyMemoryToImage vkCopyMemoryToImage; +extern PFN_vkGetDeviceImageSubresourceLayout vkGetDeviceImageSubresourceLayout; +extern PFN_vkGetImageSubresourceLayout2 vkGetImageSubresourceLayout2; +extern PFN_vkGetRenderingAreaGranularity vkGetRenderingAreaGranularity; +extern PFN_vkMapMemory2 vkMapMemory2; +extern PFN_vkTransitionImageLayout vkTransitionImageLayout; +extern PFN_vkUnmapMemory2 vkUnmapMemory2; +#endif /* defined(VK_VERSION_1_4) */ +#if defined(VK_AMDX_shader_enqueue) +extern PFN_vkCmdDispatchGraphAMDX vkCmdDispatchGraphAMDX; +extern PFN_vkCmdDispatchGraphIndirectAMDX vkCmdDispatchGraphIndirectAMDX; +extern PFN_vkCmdDispatchGraphIndirectCountAMDX vkCmdDispatchGraphIndirectCountAMDX; +extern PFN_vkCmdInitializeGraphScratchMemoryAMDX vkCmdInitializeGraphScratchMemoryAMDX; +extern PFN_vkCreateExecutionGraphPipelinesAMDX vkCreateExecutionGraphPipelinesAMDX; +extern PFN_vkGetExecutionGraphPipelineNodeIndexAMDX vkGetExecutionGraphPipelineNodeIndexAMDX; +extern PFN_vkGetExecutionGraphPipelineScratchSizeAMDX vkGetExecutionGraphPipelineScratchSizeAMDX; +#endif /* defined(VK_AMDX_shader_enqueue) */ +#if defined(VK_AMD_anti_lag) +extern PFN_vkAntiLagUpdateAMD vkAntiLagUpdateAMD; +#endif /* defined(VK_AMD_anti_lag) */ +#if defined(VK_AMD_buffer_marker) +extern PFN_vkCmdWriteBufferMarkerAMD vkCmdWriteBufferMarkerAMD; +#endif /* defined(VK_AMD_buffer_marker) */ +#if defined(VK_AMD_buffer_marker) && (defined(VK_VERSION_1_3) || defined(VK_KHR_synchronization2)) +extern PFN_vkCmdWriteBufferMarker2AMD vkCmdWriteBufferMarker2AMD; +#endif /* defined(VK_AMD_buffer_marker) && (defined(VK_VERSION_1_3) || defined(VK_KHR_synchronization2)) */ +#if defined(VK_AMD_display_native_hdr) +extern PFN_vkSetLocalDimmingAMD vkSetLocalDimmingAMD; +#endif /* defined(VK_AMD_display_native_hdr) */ +#if defined(VK_AMD_draw_indirect_count) +extern PFN_vkCmdDrawIndexedIndirectCountAMD vkCmdDrawIndexedIndirectCountAMD; +extern PFN_vkCmdDrawIndirectCountAMD vkCmdDrawIndirectCountAMD; +#endif /* defined(VK_AMD_draw_indirect_count) */ +#if defined(VK_AMD_shader_info) +extern PFN_vkGetShaderInfoAMD vkGetShaderInfoAMD; +#endif /* defined(VK_AMD_shader_info) */ +#if defined(VK_ANDROID_external_memory_android_hardware_buffer) +extern PFN_vkGetAndroidHardwareBufferPropertiesANDROID vkGetAndroidHardwareBufferPropertiesANDROID; +extern PFN_vkGetMemoryAndroidHardwareBufferANDROID vkGetMemoryAndroidHardwareBufferANDROID; +#endif /* defined(VK_ANDROID_external_memory_android_hardware_buffer) */ +#if defined(VK_EXT_acquire_drm_display) +extern PFN_vkAcquireDrmDisplayEXT vkAcquireDrmDisplayEXT; +extern PFN_vkGetDrmDisplayEXT vkGetDrmDisplayEXT; +#endif /* defined(VK_EXT_acquire_drm_display) */ +#if defined(VK_EXT_acquire_xlib_display) +extern PFN_vkAcquireXlibDisplayEXT vkAcquireXlibDisplayEXT; +extern PFN_vkGetRandROutputDisplayEXT vkGetRandROutputDisplayEXT; +#endif /* defined(VK_EXT_acquire_xlib_display) */ +#if defined(VK_EXT_attachment_feedback_loop_dynamic_state) +extern PFN_vkCmdSetAttachmentFeedbackLoopEnableEXT vkCmdSetAttachmentFeedbackLoopEnableEXT; +#endif /* defined(VK_EXT_attachment_feedback_loop_dynamic_state) */ +#if defined(VK_EXT_buffer_device_address) +extern PFN_vkGetBufferDeviceAddressEXT vkGetBufferDeviceAddressEXT; +#endif /* defined(VK_EXT_buffer_device_address) */ +#if defined(VK_EXT_calibrated_timestamps) +extern PFN_vkGetCalibratedTimestampsEXT vkGetCalibratedTimestampsEXT; +extern PFN_vkGetPhysicalDeviceCalibrateableTimeDomainsEXT vkGetPhysicalDeviceCalibrateableTimeDomainsEXT; +#endif /* defined(VK_EXT_calibrated_timestamps) */ +#if defined(VK_EXT_color_write_enable) +extern PFN_vkCmdSetColorWriteEnableEXT vkCmdSetColorWriteEnableEXT; +#endif /* defined(VK_EXT_color_write_enable) */ +#if defined(VK_EXT_conditional_rendering) +extern PFN_vkCmdBeginConditionalRenderingEXT vkCmdBeginConditionalRenderingEXT; +extern PFN_vkCmdEndConditionalRenderingEXT vkCmdEndConditionalRenderingEXT; +#endif /* defined(VK_EXT_conditional_rendering) */ +#if defined(VK_EXT_debug_marker) +extern PFN_vkCmdDebugMarkerBeginEXT vkCmdDebugMarkerBeginEXT; +extern PFN_vkCmdDebugMarkerEndEXT vkCmdDebugMarkerEndEXT; +extern PFN_vkCmdDebugMarkerInsertEXT vkCmdDebugMarkerInsertEXT; +extern PFN_vkDebugMarkerSetObjectNameEXT vkDebugMarkerSetObjectNameEXT; +extern PFN_vkDebugMarkerSetObjectTagEXT vkDebugMarkerSetObjectTagEXT; +#endif /* defined(VK_EXT_debug_marker) */ +#if defined(VK_EXT_debug_report) +extern PFN_vkCreateDebugReportCallbackEXT vkCreateDebugReportCallbackEXT; +extern PFN_vkDebugReportMessageEXT vkDebugReportMessageEXT; +extern PFN_vkDestroyDebugReportCallbackEXT vkDestroyDebugReportCallbackEXT; +#endif /* defined(VK_EXT_debug_report) */ +#if defined(VK_EXT_debug_utils) +extern PFN_vkCmdBeginDebugUtilsLabelEXT vkCmdBeginDebugUtilsLabelEXT; +extern PFN_vkCmdEndDebugUtilsLabelEXT vkCmdEndDebugUtilsLabelEXT; +extern PFN_vkCmdInsertDebugUtilsLabelEXT vkCmdInsertDebugUtilsLabelEXT; +extern PFN_vkCreateDebugUtilsMessengerEXT vkCreateDebugUtilsMessengerEXT; +extern PFN_vkDestroyDebugUtilsMessengerEXT vkDestroyDebugUtilsMessengerEXT; +extern PFN_vkQueueBeginDebugUtilsLabelEXT vkQueueBeginDebugUtilsLabelEXT; +extern PFN_vkQueueEndDebugUtilsLabelEXT vkQueueEndDebugUtilsLabelEXT; +extern PFN_vkQueueInsertDebugUtilsLabelEXT vkQueueInsertDebugUtilsLabelEXT; +extern PFN_vkSetDebugUtilsObjectNameEXT vkSetDebugUtilsObjectNameEXT; +extern PFN_vkSetDebugUtilsObjectTagEXT vkSetDebugUtilsObjectTagEXT; +extern PFN_vkSubmitDebugUtilsMessageEXT vkSubmitDebugUtilsMessageEXT; +#endif /* defined(VK_EXT_debug_utils) */ +#if defined(VK_EXT_depth_bias_control) +extern PFN_vkCmdSetDepthBias2EXT vkCmdSetDepthBias2EXT; +#endif /* defined(VK_EXT_depth_bias_control) */ +#if defined(VK_EXT_descriptor_buffer) +extern PFN_vkCmdBindDescriptorBufferEmbeddedSamplersEXT vkCmdBindDescriptorBufferEmbeddedSamplersEXT; +extern PFN_vkCmdBindDescriptorBuffersEXT vkCmdBindDescriptorBuffersEXT; +extern PFN_vkCmdSetDescriptorBufferOffsetsEXT vkCmdSetDescriptorBufferOffsetsEXT; +extern PFN_vkGetBufferOpaqueCaptureDescriptorDataEXT vkGetBufferOpaqueCaptureDescriptorDataEXT; +extern PFN_vkGetDescriptorEXT vkGetDescriptorEXT; +extern PFN_vkGetDescriptorSetLayoutBindingOffsetEXT vkGetDescriptorSetLayoutBindingOffsetEXT; +extern PFN_vkGetDescriptorSetLayoutSizeEXT vkGetDescriptorSetLayoutSizeEXT; +extern PFN_vkGetImageOpaqueCaptureDescriptorDataEXT vkGetImageOpaqueCaptureDescriptorDataEXT; +extern PFN_vkGetImageViewOpaqueCaptureDescriptorDataEXT vkGetImageViewOpaqueCaptureDescriptorDataEXT; +extern PFN_vkGetSamplerOpaqueCaptureDescriptorDataEXT vkGetSamplerOpaqueCaptureDescriptorDataEXT; +#endif /* defined(VK_EXT_descriptor_buffer) */ +#if defined(VK_EXT_descriptor_buffer) && (defined(VK_KHR_acceleration_structure) || defined(VK_NV_ray_tracing)) +extern PFN_vkGetAccelerationStructureOpaqueCaptureDescriptorDataEXT vkGetAccelerationStructureOpaqueCaptureDescriptorDataEXT; +#endif /* defined(VK_EXT_descriptor_buffer) && (defined(VK_KHR_acceleration_structure) || defined(VK_NV_ray_tracing)) */ +#if defined(VK_EXT_device_fault) +extern PFN_vkGetDeviceFaultInfoEXT vkGetDeviceFaultInfoEXT; +#endif /* defined(VK_EXT_device_fault) */ +#if defined(VK_EXT_device_generated_commands) +extern PFN_vkCmdExecuteGeneratedCommandsEXT vkCmdExecuteGeneratedCommandsEXT; +extern PFN_vkCmdPreprocessGeneratedCommandsEXT vkCmdPreprocessGeneratedCommandsEXT; +extern PFN_vkCreateIndirectCommandsLayoutEXT vkCreateIndirectCommandsLayoutEXT; +extern PFN_vkCreateIndirectExecutionSetEXT vkCreateIndirectExecutionSetEXT; +extern PFN_vkDestroyIndirectCommandsLayoutEXT vkDestroyIndirectCommandsLayoutEXT; +extern PFN_vkDestroyIndirectExecutionSetEXT vkDestroyIndirectExecutionSetEXT; +extern PFN_vkGetGeneratedCommandsMemoryRequirementsEXT vkGetGeneratedCommandsMemoryRequirementsEXT; +extern PFN_vkUpdateIndirectExecutionSetPipelineEXT vkUpdateIndirectExecutionSetPipelineEXT; +extern PFN_vkUpdateIndirectExecutionSetShaderEXT vkUpdateIndirectExecutionSetShaderEXT; +#endif /* defined(VK_EXT_device_generated_commands) */ +#if defined(VK_EXT_direct_mode_display) +extern PFN_vkReleaseDisplayEXT vkReleaseDisplayEXT; +#endif /* defined(VK_EXT_direct_mode_display) */ +#if defined(VK_EXT_directfb_surface) +extern PFN_vkCreateDirectFBSurfaceEXT vkCreateDirectFBSurfaceEXT; +extern PFN_vkGetPhysicalDeviceDirectFBPresentationSupportEXT vkGetPhysicalDeviceDirectFBPresentationSupportEXT; +#endif /* defined(VK_EXT_directfb_surface) */ +#if defined(VK_EXT_discard_rectangles) +extern PFN_vkCmdSetDiscardRectangleEXT vkCmdSetDiscardRectangleEXT; +#endif /* defined(VK_EXT_discard_rectangles) */ +#if defined(VK_EXT_discard_rectangles) && VK_EXT_DISCARD_RECTANGLES_SPEC_VERSION >= 2 +extern PFN_vkCmdSetDiscardRectangleEnableEXT vkCmdSetDiscardRectangleEnableEXT; +extern PFN_vkCmdSetDiscardRectangleModeEXT vkCmdSetDiscardRectangleModeEXT; +#endif /* defined(VK_EXT_discard_rectangles) && VK_EXT_DISCARD_RECTANGLES_SPEC_VERSION >= 2 */ +#if defined(VK_EXT_display_control) +extern PFN_vkDisplayPowerControlEXT vkDisplayPowerControlEXT; +extern PFN_vkGetSwapchainCounterEXT vkGetSwapchainCounterEXT; +extern PFN_vkRegisterDeviceEventEXT vkRegisterDeviceEventEXT; +extern PFN_vkRegisterDisplayEventEXT vkRegisterDisplayEventEXT; +#endif /* defined(VK_EXT_display_control) */ +#if defined(VK_EXT_display_surface_counter) +extern PFN_vkGetPhysicalDeviceSurfaceCapabilities2EXT vkGetPhysicalDeviceSurfaceCapabilities2EXT; +#endif /* defined(VK_EXT_display_surface_counter) */ +#if defined(VK_EXT_external_memory_host) +extern PFN_vkGetMemoryHostPointerPropertiesEXT vkGetMemoryHostPointerPropertiesEXT; +#endif /* defined(VK_EXT_external_memory_host) */ +#if defined(VK_EXT_full_screen_exclusive) +extern PFN_vkAcquireFullScreenExclusiveModeEXT vkAcquireFullScreenExclusiveModeEXT; +extern PFN_vkGetPhysicalDeviceSurfacePresentModes2EXT vkGetPhysicalDeviceSurfacePresentModes2EXT; +extern PFN_vkReleaseFullScreenExclusiveModeEXT vkReleaseFullScreenExclusiveModeEXT; +#endif /* defined(VK_EXT_full_screen_exclusive) */ +#if defined(VK_EXT_full_screen_exclusive) && (defined(VK_KHR_device_group) || defined(VK_VERSION_1_1)) +extern PFN_vkGetDeviceGroupSurfacePresentModes2EXT vkGetDeviceGroupSurfacePresentModes2EXT; +#endif /* defined(VK_EXT_full_screen_exclusive) && (defined(VK_KHR_device_group) || defined(VK_VERSION_1_1)) */ +#if defined(VK_EXT_hdr_metadata) +extern PFN_vkSetHdrMetadataEXT vkSetHdrMetadataEXT; +#endif /* defined(VK_EXT_hdr_metadata) */ +#if defined(VK_EXT_headless_surface) +extern PFN_vkCreateHeadlessSurfaceEXT vkCreateHeadlessSurfaceEXT; +#endif /* defined(VK_EXT_headless_surface) */ +#if defined(VK_EXT_host_image_copy) +extern PFN_vkCopyImageToImageEXT vkCopyImageToImageEXT; +extern PFN_vkCopyImageToMemoryEXT vkCopyImageToMemoryEXT; +extern PFN_vkCopyMemoryToImageEXT vkCopyMemoryToImageEXT; +extern PFN_vkTransitionImageLayoutEXT vkTransitionImageLayoutEXT; +#endif /* defined(VK_EXT_host_image_copy) */ +#if defined(VK_EXT_host_query_reset) +extern PFN_vkResetQueryPoolEXT vkResetQueryPoolEXT; +#endif /* defined(VK_EXT_host_query_reset) */ +#if defined(VK_EXT_image_drm_format_modifier) +extern PFN_vkGetImageDrmFormatModifierPropertiesEXT vkGetImageDrmFormatModifierPropertiesEXT; +#endif /* defined(VK_EXT_image_drm_format_modifier) */ +#if defined(VK_EXT_line_rasterization) +extern PFN_vkCmdSetLineStippleEXT vkCmdSetLineStippleEXT; +#endif /* defined(VK_EXT_line_rasterization) */ +#if defined(VK_EXT_mesh_shader) +extern PFN_vkCmdDrawMeshTasksEXT vkCmdDrawMeshTasksEXT; +extern PFN_vkCmdDrawMeshTasksIndirectEXT vkCmdDrawMeshTasksIndirectEXT; +#endif /* defined(VK_EXT_mesh_shader) */ +#if defined(VK_EXT_mesh_shader) && (defined(VK_KHR_draw_indirect_count) || defined(VK_VERSION_1_2)) +extern PFN_vkCmdDrawMeshTasksIndirectCountEXT vkCmdDrawMeshTasksIndirectCountEXT; +#endif /* defined(VK_EXT_mesh_shader) && (defined(VK_KHR_draw_indirect_count) || defined(VK_VERSION_1_2)) */ +#if defined(VK_EXT_metal_objects) +extern PFN_vkExportMetalObjectsEXT vkExportMetalObjectsEXT; +#endif /* defined(VK_EXT_metal_objects) */ +#if defined(VK_EXT_metal_surface) +extern PFN_vkCreateMetalSurfaceEXT vkCreateMetalSurfaceEXT; +#endif /* defined(VK_EXT_metal_surface) */ +#if defined(VK_EXT_multi_draw) +extern PFN_vkCmdDrawMultiEXT vkCmdDrawMultiEXT; +extern PFN_vkCmdDrawMultiIndexedEXT vkCmdDrawMultiIndexedEXT; +#endif /* defined(VK_EXT_multi_draw) */ +#if defined(VK_EXT_opacity_micromap) +extern PFN_vkBuildMicromapsEXT vkBuildMicromapsEXT; +extern PFN_vkCmdBuildMicromapsEXT vkCmdBuildMicromapsEXT; +extern PFN_vkCmdCopyMemoryToMicromapEXT vkCmdCopyMemoryToMicromapEXT; +extern PFN_vkCmdCopyMicromapEXT vkCmdCopyMicromapEXT; +extern PFN_vkCmdCopyMicromapToMemoryEXT vkCmdCopyMicromapToMemoryEXT; +extern PFN_vkCmdWriteMicromapsPropertiesEXT vkCmdWriteMicromapsPropertiesEXT; +extern PFN_vkCopyMemoryToMicromapEXT vkCopyMemoryToMicromapEXT; +extern PFN_vkCopyMicromapEXT vkCopyMicromapEXT; +extern PFN_vkCopyMicromapToMemoryEXT vkCopyMicromapToMemoryEXT; +extern PFN_vkCreateMicromapEXT vkCreateMicromapEXT; +extern PFN_vkDestroyMicromapEXT vkDestroyMicromapEXT; +extern PFN_vkGetDeviceMicromapCompatibilityEXT vkGetDeviceMicromapCompatibilityEXT; +extern PFN_vkGetMicromapBuildSizesEXT vkGetMicromapBuildSizesEXT; +extern PFN_vkWriteMicromapsPropertiesEXT vkWriteMicromapsPropertiesEXT; +#endif /* defined(VK_EXT_opacity_micromap) */ +#if defined(VK_EXT_pageable_device_local_memory) +extern PFN_vkSetDeviceMemoryPriorityEXT vkSetDeviceMemoryPriorityEXT; +#endif /* defined(VK_EXT_pageable_device_local_memory) */ +#if defined(VK_EXT_pipeline_properties) +extern PFN_vkGetPipelinePropertiesEXT vkGetPipelinePropertiesEXT; +#endif /* defined(VK_EXT_pipeline_properties) */ +#if defined(VK_EXT_private_data) +extern PFN_vkCreatePrivateDataSlotEXT vkCreatePrivateDataSlotEXT; +extern PFN_vkDestroyPrivateDataSlotEXT vkDestroyPrivateDataSlotEXT; +extern PFN_vkGetPrivateDataEXT vkGetPrivateDataEXT; +extern PFN_vkSetPrivateDataEXT vkSetPrivateDataEXT; +#endif /* defined(VK_EXT_private_data) */ +#if defined(VK_EXT_sample_locations) +extern PFN_vkCmdSetSampleLocationsEXT vkCmdSetSampleLocationsEXT; +extern PFN_vkGetPhysicalDeviceMultisamplePropertiesEXT vkGetPhysicalDeviceMultisamplePropertiesEXT; +#endif /* defined(VK_EXT_sample_locations) */ +#if defined(VK_EXT_shader_module_identifier) +extern PFN_vkGetShaderModuleCreateInfoIdentifierEXT vkGetShaderModuleCreateInfoIdentifierEXT; +extern PFN_vkGetShaderModuleIdentifierEXT vkGetShaderModuleIdentifierEXT; +#endif /* defined(VK_EXT_shader_module_identifier) */ +#if defined(VK_EXT_shader_object) +extern PFN_vkCmdBindShadersEXT vkCmdBindShadersEXT; +extern PFN_vkCreateShadersEXT vkCreateShadersEXT; +extern PFN_vkDestroyShaderEXT vkDestroyShaderEXT; +extern PFN_vkGetShaderBinaryDataEXT vkGetShaderBinaryDataEXT; +#endif /* defined(VK_EXT_shader_object) */ +#if defined(VK_EXT_swapchain_maintenance1) +extern PFN_vkReleaseSwapchainImagesEXT vkReleaseSwapchainImagesEXT; +#endif /* defined(VK_EXT_swapchain_maintenance1) */ +#if defined(VK_EXT_tooling_info) +extern PFN_vkGetPhysicalDeviceToolPropertiesEXT vkGetPhysicalDeviceToolPropertiesEXT; +#endif /* defined(VK_EXT_tooling_info) */ +#if defined(VK_EXT_transform_feedback) +extern PFN_vkCmdBeginQueryIndexedEXT vkCmdBeginQueryIndexedEXT; +extern PFN_vkCmdBeginTransformFeedbackEXT vkCmdBeginTransformFeedbackEXT; +extern PFN_vkCmdBindTransformFeedbackBuffersEXT vkCmdBindTransformFeedbackBuffersEXT; +extern PFN_vkCmdDrawIndirectByteCountEXT vkCmdDrawIndirectByteCountEXT; +extern PFN_vkCmdEndQueryIndexedEXT vkCmdEndQueryIndexedEXT; +extern PFN_vkCmdEndTransformFeedbackEXT vkCmdEndTransformFeedbackEXT; +#endif /* defined(VK_EXT_transform_feedback) */ +#if defined(VK_EXT_validation_cache) +extern PFN_vkCreateValidationCacheEXT vkCreateValidationCacheEXT; +extern PFN_vkDestroyValidationCacheEXT vkDestroyValidationCacheEXT; +extern PFN_vkGetValidationCacheDataEXT vkGetValidationCacheDataEXT; +extern PFN_vkMergeValidationCachesEXT vkMergeValidationCachesEXT; +#endif /* defined(VK_EXT_validation_cache) */ +#if defined(VK_FUCHSIA_buffer_collection) +extern PFN_vkCreateBufferCollectionFUCHSIA vkCreateBufferCollectionFUCHSIA; +extern PFN_vkDestroyBufferCollectionFUCHSIA vkDestroyBufferCollectionFUCHSIA; +extern PFN_vkGetBufferCollectionPropertiesFUCHSIA vkGetBufferCollectionPropertiesFUCHSIA; +extern PFN_vkSetBufferCollectionBufferConstraintsFUCHSIA vkSetBufferCollectionBufferConstraintsFUCHSIA; +extern PFN_vkSetBufferCollectionImageConstraintsFUCHSIA vkSetBufferCollectionImageConstraintsFUCHSIA; +#endif /* defined(VK_FUCHSIA_buffer_collection) */ +#if defined(VK_FUCHSIA_external_memory) +extern PFN_vkGetMemoryZirconHandleFUCHSIA vkGetMemoryZirconHandleFUCHSIA; +extern PFN_vkGetMemoryZirconHandlePropertiesFUCHSIA vkGetMemoryZirconHandlePropertiesFUCHSIA; +#endif /* defined(VK_FUCHSIA_external_memory) */ +#if defined(VK_FUCHSIA_external_semaphore) +extern PFN_vkGetSemaphoreZirconHandleFUCHSIA vkGetSemaphoreZirconHandleFUCHSIA; +extern PFN_vkImportSemaphoreZirconHandleFUCHSIA vkImportSemaphoreZirconHandleFUCHSIA; +#endif /* defined(VK_FUCHSIA_external_semaphore) */ +#if defined(VK_FUCHSIA_imagepipe_surface) +extern PFN_vkCreateImagePipeSurfaceFUCHSIA vkCreateImagePipeSurfaceFUCHSIA; +#endif /* defined(VK_FUCHSIA_imagepipe_surface) */ +#if defined(VK_GGP_stream_descriptor_surface) +extern PFN_vkCreateStreamDescriptorSurfaceGGP vkCreateStreamDescriptorSurfaceGGP; +#endif /* defined(VK_GGP_stream_descriptor_surface) */ +#if defined(VK_GOOGLE_display_timing) +extern PFN_vkGetPastPresentationTimingGOOGLE vkGetPastPresentationTimingGOOGLE; +extern PFN_vkGetRefreshCycleDurationGOOGLE vkGetRefreshCycleDurationGOOGLE; +#endif /* defined(VK_GOOGLE_display_timing) */ +#if defined(VK_HUAWEI_cluster_culling_shader) +extern PFN_vkCmdDrawClusterHUAWEI vkCmdDrawClusterHUAWEI; +extern PFN_vkCmdDrawClusterIndirectHUAWEI vkCmdDrawClusterIndirectHUAWEI; +#endif /* defined(VK_HUAWEI_cluster_culling_shader) */ +#if defined(VK_HUAWEI_invocation_mask) +extern PFN_vkCmdBindInvocationMaskHUAWEI vkCmdBindInvocationMaskHUAWEI; +#endif /* defined(VK_HUAWEI_invocation_mask) */ +#if defined(VK_HUAWEI_subpass_shading) && VK_HUAWEI_SUBPASS_SHADING_SPEC_VERSION >= 2 +extern PFN_vkGetDeviceSubpassShadingMaxWorkgroupSizeHUAWEI vkGetDeviceSubpassShadingMaxWorkgroupSizeHUAWEI; +#endif /* defined(VK_HUAWEI_subpass_shading) && VK_HUAWEI_SUBPASS_SHADING_SPEC_VERSION >= 2 */ +#if defined(VK_HUAWEI_subpass_shading) +extern PFN_vkCmdSubpassShadingHUAWEI vkCmdSubpassShadingHUAWEI; +#endif /* defined(VK_HUAWEI_subpass_shading) */ +#if defined(VK_INTEL_performance_query) +extern PFN_vkAcquirePerformanceConfigurationINTEL vkAcquirePerformanceConfigurationINTEL; +extern PFN_vkCmdSetPerformanceMarkerINTEL vkCmdSetPerformanceMarkerINTEL; +extern PFN_vkCmdSetPerformanceOverrideINTEL vkCmdSetPerformanceOverrideINTEL; +extern PFN_vkCmdSetPerformanceStreamMarkerINTEL vkCmdSetPerformanceStreamMarkerINTEL; +extern PFN_vkGetPerformanceParameterINTEL vkGetPerformanceParameterINTEL; +extern PFN_vkInitializePerformanceApiINTEL vkInitializePerformanceApiINTEL; +extern PFN_vkQueueSetPerformanceConfigurationINTEL vkQueueSetPerformanceConfigurationINTEL; +extern PFN_vkReleasePerformanceConfigurationINTEL vkReleasePerformanceConfigurationINTEL; +extern PFN_vkUninitializePerformanceApiINTEL vkUninitializePerformanceApiINTEL; +#endif /* defined(VK_INTEL_performance_query) */ +#if defined(VK_KHR_acceleration_structure) +extern PFN_vkBuildAccelerationStructuresKHR vkBuildAccelerationStructuresKHR; +extern PFN_vkCmdBuildAccelerationStructuresIndirectKHR vkCmdBuildAccelerationStructuresIndirectKHR; +extern PFN_vkCmdBuildAccelerationStructuresKHR vkCmdBuildAccelerationStructuresKHR; +extern PFN_vkCmdCopyAccelerationStructureKHR vkCmdCopyAccelerationStructureKHR; +extern PFN_vkCmdCopyAccelerationStructureToMemoryKHR vkCmdCopyAccelerationStructureToMemoryKHR; +extern PFN_vkCmdCopyMemoryToAccelerationStructureKHR vkCmdCopyMemoryToAccelerationStructureKHR; +extern PFN_vkCmdWriteAccelerationStructuresPropertiesKHR vkCmdWriteAccelerationStructuresPropertiesKHR; +extern PFN_vkCopyAccelerationStructureKHR vkCopyAccelerationStructureKHR; +extern PFN_vkCopyAccelerationStructureToMemoryKHR vkCopyAccelerationStructureToMemoryKHR; +extern PFN_vkCopyMemoryToAccelerationStructureKHR vkCopyMemoryToAccelerationStructureKHR; +extern PFN_vkCreateAccelerationStructureKHR vkCreateAccelerationStructureKHR; +extern PFN_vkDestroyAccelerationStructureKHR vkDestroyAccelerationStructureKHR; +extern PFN_vkGetAccelerationStructureBuildSizesKHR vkGetAccelerationStructureBuildSizesKHR; +extern PFN_vkGetAccelerationStructureDeviceAddressKHR vkGetAccelerationStructureDeviceAddressKHR; +extern PFN_vkGetDeviceAccelerationStructureCompatibilityKHR vkGetDeviceAccelerationStructureCompatibilityKHR; +extern PFN_vkWriteAccelerationStructuresPropertiesKHR vkWriteAccelerationStructuresPropertiesKHR; +#endif /* defined(VK_KHR_acceleration_structure) */ +#if defined(VK_KHR_android_surface) +extern PFN_vkCreateAndroidSurfaceKHR vkCreateAndroidSurfaceKHR; +#endif /* defined(VK_KHR_android_surface) */ +#if defined(VK_KHR_bind_memory2) +extern PFN_vkBindBufferMemory2KHR vkBindBufferMemory2KHR; +extern PFN_vkBindImageMemory2KHR vkBindImageMemory2KHR; +#endif /* defined(VK_KHR_bind_memory2) */ +#if defined(VK_KHR_buffer_device_address) +extern PFN_vkGetBufferDeviceAddressKHR vkGetBufferDeviceAddressKHR; +extern PFN_vkGetBufferOpaqueCaptureAddressKHR vkGetBufferOpaqueCaptureAddressKHR; +extern PFN_vkGetDeviceMemoryOpaqueCaptureAddressKHR vkGetDeviceMemoryOpaqueCaptureAddressKHR; +#endif /* defined(VK_KHR_buffer_device_address) */ +#if defined(VK_KHR_calibrated_timestamps) +extern PFN_vkGetCalibratedTimestampsKHR vkGetCalibratedTimestampsKHR; +extern PFN_vkGetPhysicalDeviceCalibrateableTimeDomainsKHR vkGetPhysicalDeviceCalibrateableTimeDomainsKHR; +#endif /* defined(VK_KHR_calibrated_timestamps) */ +#if defined(VK_KHR_cooperative_matrix) +extern PFN_vkGetPhysicalDeviceCooperativeMatrixPropertiesKHR vkGetPhysicalDeviceCooperativeMatrixPropertiesKHR; +#endif /* defined(VK_KHR_cooperative_matrix) */ +#if defined(VK_KHR_copy_commands2) +extern PFN_vkCmdBlitImage2KHR vkCmdBlitImage2KHR; +extern PFN_vkCmdCopyBuffer2KHR vkCmdCopyBuffer2KHR; +extern PFN_vkCmdCopyBufferToImage2KHR vkCmdCopyBufferToImage2KHR; +extern PFN_vkCmdCopyImage2KHR vkCmdCopyImage2KHR; +extern PFN_vkCmdCopyImageToBuffer2KHR vkCmdCopyImageToBuffer2KHR; +extern PFN_vkCmdResolveImage2KHR vkCmdResolveImage2KHR; +#endif /* defined(VK_KHR_copy_commands2) */ +#if defined(VK_KHR_create_renderpass2) +extern PFN_vkCmdBeginRenderPass2KHR vkCmdBeginRenderPass2KHR; +extern PFN_vkCmdEndRenderPass2KHR vkCmdEndRenderPass2KHR; +extern PFN_vkCmdNextSubpass2KHR vkCmdNextSubpass2KHR; +extern PFN_vkCreateRenderPass2KHR vkCreateRenderPass2KHR; +#endif /* defined(VK_KHR_create_renderpass2) */ +#if defined(VK_KHR_deferred_host_operations) +extern PFN_vkCreateDeferredOperationKHR vkCreateDeferredOperationKHR; +extern PFN_vkDeferredOperationJoinKHR vkDeferredOperationJoinKHR; +extern PFN_vkDestroyDeferredOperationKHR vkDestroyDeferredOperationKHR; +extern PFN_vkGetDeferredOperationMaxConcurrencyKHR vkGetDeferredOperationMaxConcurrencyKHR; +extern PFN_vkGetDeferredOperationResultKHR vkGetDeferredOperationResultKHR; +#endif /* defined(VK_KHR_deferred_host_operations) */ +#if defined(VK_KHR_descriptor_update_template) +extern PFN_vkCreateDescriptorUpdateTemplateKHR vkCreateDescriptorUpdateTemplateKHR; +extern PFN_vkDestroyDescriptorUpdateTemplateKHR vkDestroyDescriptorUpdateTemplateKHR; +extern PFN_vkUpdateDescriptorSetWithTemplateKHR vkUpdateDescriptorSetWithTemplateKHR; +#endif /* defined(VK_KHR_descriptor_update_template) */ +#if defined(VK_KHR_device_group) +extern PFN_vkCmdDispatchBaseKHR vkCmdDispatchBaseKHR; +extern PFN_vkCmdSetDeviceMaskKHR vkCmdSetDeviceMaskKHR; +extern PFN_vkGetDeviceGroupPeerMemoryFeaturesKHR vkGetDeviceGroupPeerMemoryFeaturesKHR; +#endif /* defined(VK_KHR_device_group) */ +#if defined(VK_KHR_device_group_creation) +extern PFN_vkEnumeratePhysicalDeviceGroupsKHR vkEnumeratePhysicalDeviceGroupsKHR; +#endif /* defined(VK_KHR_device_group_creation) */ +#if defined(VK_KHR_display) +extern PFN_vkCreateDisplayModeKHR vkCreateDisplayModeKHR; +extern PFN_vkCreateDisplayPlaneSurfaceKHR vkCreateDisplayPlaneSurfaceKHR; +extern PFN_vkGetDisplayModePropertiesKHR vkGetDisplayModePropertiesKHR; +extern PFN_vkGetDisplayPlaneCapabilitiesKHR vkGetDisplayPlaneCapabilitiesKHR; +extern PFN_vkGetDisplayPlaneSupportedDisplaysKHR vkGetDisplayPlaneSupportedDisplaysKHR; +extern PFN_vkGetPhysicalDeviceDisplayPlanePropertiesKHR vkGetPhysicalDeviceDisplayPlanePropertiesKHR; +extern PFN_vkGetPhysicalDeviceDisplayPropertiesKHR vkGetPhysicalDeviceDisplayPropertiesKHR; +#endif /* defined(VK_KHR_display) */ +#if defined(VK_KHR_display_swapchain) +extern PFN_vkCreateSharedSwapchainsKHR vkCreateSharedSwapchainsKHR; +#endif /* defined(VK_KHR_display_swapchain) */ +#if defined(VK_KHR_draw_indirect_count) +extern PFN_vkCmdDrawIndexedIndirectCountKHR vkCmdDrawIndexedIndirectCountKHR; +extern PFN_vkCmdDrawIndirectCountKHR vkCmdDrawIndirectCountKHR; +#endif /* defined(VK_KHR_draw_indirect_count) */ +#if defined(VK_KHR_dynamic_rendering) +extern PFN_vkCmdBeginRenderingKHR vkCmdBeginRenderingKHR; +extern PFN_vkCmdEndRenderingKHR vkCmdEndRenderingKHR; +#endif /* defined(VK_KHR_dynamic_rendering) */ +#if defined(VK_KHR_dynamic_rendering_local_read) +extern PFN_vkCmdSetRenderingAttachmentLocationsKHR vkCmdSetRenderingAttachmentLocationsKHR; +extern PFN_vkCmdSetRenderingInputAttachmentIndicesKHR vkCmdSetRenderingInputAttachmentIndicesKHR; +#endif /* defined(VK_KHR_dynamic_rendering_local_read) */ +#if defined(VK_KHR_external_fence_capabilities) +extern PFN_vkGetPhysicalDeviceExternalFencePropertiesKHR vkGetPhysicalDeviceExternalFencePropertiesKHR; +#endif /* defined(VK_KHR_external_fence_capabilities) */ +#if defined(VK_KHR_external_fence_fd) +extern PFN_vkGetFenceFdKHR vkGetFenceFdKHR; +extern PFN_vkImportFenceFdKHR vkImportFenceFdKHR; +#endif /* defined(VK_KHR_external_fence_fd) */ +#if defined(VK_KHR_external_fence_win32) +extern PFN_vkGetFenceWin32HandleKHR vkGetFenceWin32HandleKHR; +extern PFN_vkImportFenceWin32HandleKHR vkImportFenceWin32HandleKHR; +#endif /* defined(VK_KHR_external_fence_win32) */ +#if defined(VK_KHR_external_memory_capabilities) +extern PFN_vkGetPhysicalDeviceExternalBufferPropertiesKHR vkGetPhysicalDeviceExternalBufferPropertiesKHR; +#endif /* defined(VK_KHR_external_memory_capabilities) */ +#if defined(VK_KHR_external_memory_fd) +extern PFN_vkGetMemoryFdKHR vkGetMemoryFdKHR; +extern PFN_vkGetMemoryFdPropertiesKHR vkGetMemoryFdPropertiesKHR; +#endif /* defined(VK_KHR_external_memory_fd) */ +#if defined(VK_KHR_external_memory_win32) +extern PFN_vkGetMemoryWin32HandleKHR vkGetMemoryWin32HandleKHR; +extern PFN_vkGetMemoryWin32HandlePropertiesKHR vkGetMemoryWin32HandlePropertiesKHR; +#endif /* defined(VK_KHR_external_memory_win32) */ +#if defined(VK_KHR_external_semaphore_capabilities) +extern PFN_vkGetPhysicalDeviceExternalSemaphorePropertiesKHR vkGetPhysicalDeviceExternalSemaphorePropertiesKHR; +#endif /* defined(VK_KHR_external_semaphore_capabilities) */ +#if defined(VK_KHR_external_semaphore_fd) +extern PFN_vkGetSemaphoreFdKHR vkGetSemaphoreFdKHR; +extern PFN_vkImportSemaphoreFdKHR vkImportSemaphoreFdKHR; +#endif /* defined(VK_KHR_external_semaphore_fd) */ +#if defined(VK_KHR_external_semaphore_win32) +extern PFN_vkGetSemaphoreWin32HandleKHR vkGetSemaphoreWin32HandleKHR; +extern PFN_vkImportSemaphoreWin32HandleKHR vkImportSemaphoreWin32HandleKHR; +#endif /* defined(VK_KHR_external_semaphore_win32) */ +#if defined(VK_KHR_fragment_shading_rate) +extern PFN_vkCmdSetFragmentShadingRateKHR vkCmdSetFragmentShadingRateKHR; +extern PFN_vkGetPhysicalDeviceFragmentShadingRatesKHR vkGetPhysicalDeviceFragmentShadingRatesKHR; +#endif /* defined(VK_KHR_fragment_shading_rate) */ +#if defined(VK_KHR_get_display_properties2) +extern PFN_vkGetDisplayModeProperties2KHR vkGetDisplayModeProperties2KHR; +extern PFN_vkGetDisplayPlaneCapabilities2KHR vkGetDisplayPlaneCapabilities2KHR; +extern PFN_vkGetPhysicalDeviceDisplayPlaneProperties2KHR vkGetPhysicalDeviceDisplayPlaneProperties2KHR; +extern PFN_vkGetPhysicalDeviceDisplayProperties2KHR vkGetPhysicalDeviceDisplayProperties2KHR; +#endif /* defined(VK_KHR_get_display_properties2) */ +#if defined(VK_KHR_get_memory_requirements2) +extern PFN_vkGetBufferMemoryRequirements2KHR vkGetBufferMemoryRequirements2KHR; +extern PFN_vkGetImageMemoryRequirements2KHR vkGetImageMemoryRequirements2KHR; +extern PFN_vkGetImageSparseMemoryRequirements2KHR vkGetImageSparseMemoryRequirements2KHR; +#endif /* defined(VK_KHR_get_memory_requirements2) */ +#if defined(VK_KHR_get_physical_device_properties2) +extern PFN_vkGetPhysicalDeviceFeatures2KHR vkGetPhysicalDeviceFeatures2KHR; +extern PFN_vkGetPhysicalDeviceFormatProperties2KHR vkGetPhysicalDeviceFormatProperties2KHR; +extern PFN_vkGetPhysicalDeviceImageFormatProperties2KHR vkGetPhysicalDeviceImageFormatProperties2KHR; +extern PFN_vkGetPhysicalDeviceMemoryProperties2KHR vkGetPhysicalDeviceMemoryProperties2KHR; +extern PFN_vkGetPhysicalDeviceProperties2KHR vkGetPhysicalDeviceProperties2KHR; +extern PFN_vkGetPhysicalDeviceQueueFamilyProperties2KHR vkGetPhysicalDeviceQueueFamilyProperties2KHR; +extern PFN_vkGetPhysicalDeviceSparseImageFormatProperties2KHR vkGetPhysicalDeviceSparseImageFormatProperties2KHR; +#endif /* defined(VK_KHR_get_physical_device_properties2) */ +#if defined(VK_KHR_get_surface_capabilities2) +extern PFN_vkGetPhysicalDeviceSurfaceCapabilities2KHR vkGetPhysicalDeviceSurfaceCapabilities2KHR; +extern PFN_vkGetPhysicalDeviceSurfaceFormats2KHR vkGetPhysicalDeviceSurfaceFormats2KHR; +#endif /* defined(VK_KHR_get_surface_capabilities2) */ +#if defined(VK_KHR_line_rasterization) +extern PFN_vkCmdSetLineStippleKHR vkCmdSetLineStippleKHR; +#endif /* defined(VK_KHR_line_rasterization) */ +#if defined(VK_KHR_maintenance1) +extern PFN_vkTrimCommandPoolKHR vkTrimCommandPoolKHR; +#endif /* defined(VK_KHR_maintenance1) */ +#if defined(VK_KHR_maintenance3) +extern PFN_vkGetDescriptorSetLayoutSupportKHR vkGetDescriptorSetLayoutSupportKHR; +#endif /* defined(VK_KHR_maintenance3) */ +#if defined(VK_KHR_maintenance4) +extern PFN_vkGetDeviceBufferMemoryRequirementsKHR vkGetDeviceBufferMemoryRequirementsKHR; +extern PFN_vkGetDeviceImageMemoryRequirementsKHR vkGetDeviceImageMemoryRequirementsKHR; +extern PFN_vkGetDeviceImageSparseMemoryRequirementsKHR vkGetDeviceImageSparseMemoryRequirementsKHR; +#endif /* defined(VK_KHR_maintenance4) */ +#if defined(VK_KHR_maintenance5) +extern PFN_vkCmdBindIndexBuffer2KHR vkCmdBindIndexBuffer2KHR; +extern PFN_vkGetDeviceImageSubresourceLayoutKHR vkGetDeviceImageSubresourceLayoutKHR; +extern PFN_vkGetImageSubresourceLayout2KHR vkGetImageSubresourceLayout2KHR; +extern PFN_vkGetRenderingAreaGranularityKHR vkGetRenderingAreaGranularityKHR; +#endif /* defined(VK_KHR_maintenance5) */ +#if defined(VK_KHR_maintenance6) +extern PFN_vkCmdBindDescriptorSets2KHR vkCmdBindDescriptorSets2KHR; +extern PFN_vkCmdPushConstants2KHR vkCmdPushConstants2KHR; +#endif /* defined(VK_KHR_maintenance6) */ +#if defined(VK_KHR_maintenance6) && defined(VK_KHR_push_descriptor) +extern PFN_vkCmdPushDescriptorSet2KHR vkCmdPushDescriptorSet2KHR; +extern PFN_vkCmdPushDescriptorSetWithTemplate2KHR vkCmdPushDescriptorSetWithTemplate2KHR; +#endif /* defined(VK_KHR_maintenance6) && defined(VK_KHR_push_descriptor) */ +#if defined(VK_KHR_maintenance6) && defined(VK_EXT_descriptor_buffer) +extern PFN_vkCmdBindDescriptorBufferEmbeddedSamplers2EXT vkCmdBindDescriptorBufferEmbeddedSamplers2EXT; +extern PFN_vkCmdSetDescriptorBufferOffsets2EXT vkCmdSetDescriptorBufferOffsets2EXT; +#endif /* defined(VK_KHR_maintenance6) && defined(VK_EXT_descriptor_buffer) */ +#if defined(VK_KHR_map_memory2) +extern PFN_vkMapMemory2KHR vkMapMemory2KHR; +extern PFN_vkUnmapMemory2KHR vkUnmapMemory2KHR; +#endif /* defined(VK_KHR_map_memory2) */ +#if defined(VK_KHR_performance_query) +extern PFN_vkAcquireProfilingLockKHR vkAcquireProfilingLockKHR; +extern PFN_vkEnumeratePhysicalDeviceQueueFamilyPerformanceQueryCountersKHR vkEnumeratePhysicalDeviceQueueFamilyPerformanceQueryCountersKHR; +extern PFN_vkGetPhysicalDeviceQueueFamilyPerformanceQueryPassesKHR vkGetPhysicalDeviceQueueFamilyPerformanceQueryPassesKHR; +extern PFN_vkReleaseProfilingLockKHR vkReleaseProfilingLockKHR; +#endif /* defined(VK_KHR_performance_query) */ +#if defined(VK_KHR_pipeline_binary) +extern PFN_vkCreatePipelineBinariesKHR vkCreatePipelineBinariesKHR; +extern PFN_vkDestroyPipelineBinaryKHR vkDestroyPipelineBinaryKHR; +extern PFN_vkGetPipelineBinaryDataKHR vkGetPipelineBinaryDataKHR; +extern PFN_vkGetPipelineKeyKHR vkGetPipelineKeyKHR; +extern PFN_vkReleaseCapturedPipelineDataKHR vkReleaseCapturedPipelineDataKHR; +#endif /* defined(VK_KHR_pipeline_binary) */ +#if defined(VK_KHR_pipeline_executable_properties) +extern PFN_vkGetPipelineExecutableInternalRepresentationsKHR vkGetPipelineExecutableInternalRepresentationsKHR; +extern PFN_vkGetPipelineExecutablePropertiesKHR vkGetPipelineExecutablePropertiesKHR; +extern PFN_vkGetPipelineExecutableStatisticsKHR vkGetPipelineExecutableStatisticsKHR; +#endif /* defined(VK_KHR_pipeline_executable_properties) */ +#if defined(VK_KHR_present_wait) +extern PFN_vkWaitForPresentKHR vkWaitForPresentKHR; +#endif /* defined(VK_KHR_present_wait) */ +#if defined(VK_KHR_push_descriptor) +extern PFN_vkCmdPushDescriptorSetKHR vkCmdPushDescriptorSetKHR; +#endif /* defined(VK_KHR_push_descriptor) */ +#if defined(VK_KHR_ray_tracing_maintenance1) && defined(VK_KHR_ray_tracing_pipeline) +extern PFN_vkCmdTraceRaysIndirect2KHR vkCmdTraceRaysIndirect2KHR; +#endif /* defined(VK_KHR_ray_tracing_maintenance1) && defined(VK_KHR_ray_tracing_pipeline) */ +#if defined(VK_KHR_ray_tracing_pipeline) +extern PFN_vkCmdSetRayTracingPipelineStackSizeKHR vkCmdSetRayTracingPipelineStackSizeKHR; +extern PFN_vkCmdTraceRaysIndirectKHR vkCmdTraceRaysIndirectKHR; +extern PFN_vkCmdTraceRaysKHR vkCmdTraceRaysKHR; +extern PFN_vkCreateRayTracingPipelinesKHR vkCreateRayTracingPipelinesKHR; +extern PFN_vkGetRayTracingCaptureReplayShaderGroupHandlesKHR vkGetRayTracingCaptureReplayShaderGroupHandlesKHR; +extern PFN_vkGetRayTracingShaderGroupHandlesKHR vkGetRayTracingShaderGroupHandlesKHR; +extern PFN_vkGetRayTracingShaderGroupStackSizeKHR vkGetRayTracingShaderGroupStackSizeKHR; +#endif /* defined(VK_KHR_ray_tracing_pipeline) */ +#if defined(VK_KHR_sampler_ycbcr_conversion) +extern PFN_vkCreateSamplerYcbcrConversionKHR vkCreateSamplerYcbcrConversionKHR; +extern PFN_vkDestroySamplerYcbcrConversionKHR vkDestroySamplerYcbcrConversionKHR; +#endif /* defined(VK_KHR_sampler_ycbcr_conversion) */ +#if defined(VK_KHR_shared_presentable_image) +extern PFN_vkGetSwapchainStatusKHR vkGetSwapchainStatusKHR; +#endif /* defined(VK_KHR_shared_presentable_image) */ +#if defined(VK_KHR_surface) +extern PFN_vkDestroySurfaceKHR vkDestroySurfaceKHR; +extern PFN_vkGetPhysicalDeviceSurfaceCapabilitiesKHR vkGetPhysicalDeviceSurfaceCapabilitiesKHR; +extern PFN_vkGetPhysicalDeviceSurfaceFormatsKHR vkGetPhysicalDeviceSurfaceFormatsKHR; +extern PFN_vkGetPhysicalDeviceSurfacePresentModesKHR vkGetPhysicalDeviceSurfacePresentModesKHR; +extern PFN_vkGetPhysicalDeviceSurfaceSupportKHR vkGetPhysicalDeviceSurfaceSupportKHR; +#endif /* defined(VK_KHR_surface) */ +#if defined(VK_KHR_swapchain) +extern PFN_vkAcquireNextImageKHR vkAcquireNextImageKHR; +extern PFN_vkCreateSwapchainKHR vkCreateSwapchainKHR; +extern PFN_vkDestroySwapchainKHR vkDestroySwapchainKHR; +extern PFN_vkGetSwapchainImagesKHR vkGetSwapchainImagesKHR; +extern PFN_vkQueuePresentKHR vkQueuePresentKHR; +#endif /* defined(VK_KHR_swapchain) */ +#if defined(VK_KHR_synchronization2) +extern PFN_vkCmdPipelineBarrier2KHR vkCmdPipelineBarrier2KHR; +extern PFN_vkCmdResetEvent2KHR vkCmdResetEvent2KHR; +extern PFN_vkCmdSetEvent2KHR vkCmdSetEvent2KHR; +extern PFN_vkCmdWaitEvents2KHR vkCmdWaitEvents2KHR; +extern PFN_vkCmdWriteTimestamp2KHR vkCmdWriteTimestamp2KHR; +extern PFN_vkQueueSubmit2KHR vkQueueSubmit2KHR; +#endif /* defined(VK_KHR_synchronization2) */ +#if defined(VK_KHR_timeline_semaphore) +extern PFN_vkGetSemaphoreCounterValueKHR vkGetSemaphoreCounterValueKHR; +extern PFN_vkSignalSemaphoreKHR vkSignalSemaphoreKHR; +extern PFN_vkWaitSemaphoresKHR vkWaitSemaphoresKHR; +#endif /* defined(VK_KHR_timeline_semaphore) */ +#if defined(VK_KHR_video_decode_queue) +extern PFN_vkCmdDecodeVideoKHR vkCmdDecodeVideoKHR; +#endif /* defined(VK_KHR_video_decode_queue) */ +#if defined(VK_KHR_video_encode_queue) +extern PFN_vkCmdEncodeVideoKHR vkCmdEncodeVideoKHR; +extern PFN_vkGetEncodedVideoSessionParametersKHR vkGetEncodedVideoSessionParametersKHR; +extern PFN_vkGetPhysicalDeviceVideoEncodeQualityLevelPropertiesKHR vkGetPhysicalDeviceVideoEncodeQualityLevelPropertiesKHR; +#endif /* defined(VK_KHR_video_encode_queue) */ +#if defined(VK_KHR_video_queue) +extern PFN_vkBindVideoSessionMemoryKHR vkBindVideoSessionMemoryKHR; +extern PFN_vkCmdBeginVideoCodingKHR vkCmdBeginVideoCodingKHR; +extern PFN_vkCmdControlVideoCodingKHR vkCmdControlVideoCodingKHR; +extern PFN_vkCmdEndVideoCodingKHR vkCmdEndVideoCodingKHR; +extern PFN_vkCreateVideoSessionKHR vkCreateVideoSessionKHR; +extern PFN_vkCreateVideoSessionParametersKHR vkCreateVideoSessionParametersKHR; +extern PFN_vkDestroyVideoSessionKHR vkDestroyVideoSessionKHR; +extern PFN_vkDestroyVideoSessionParametersKHR vkDestroyVideoSessionParametersKHR; +extern PFN_vkGetPhysicalDeviceVideoCapabilitiesKHR vkGetPhysicalDeviceVideoCapabilitiesKHR; +extern PFN_vkGetPhysicalDeviceVideoFormatPropertiesKHR vkGetPhysicalDeviceVideoFormatPropertiesKHR; +extern PFN_vkGetVideoSessionMemoryRequirementsKHR vkGetVideoSessionMemoryRequirementsKHR; +extern PFN_vkUpdateVideoSessionParametersKHR vkUpdateVideoSessionParametersKHR; +#endif /* defined(VK_KHR_video_queue) */ +#if defined(VK_KHR_wayland_surface) +extern PFN_vkCreateWaylandSurfaceKHR vkCreateWaylandSurfaceKHR; +extern PFN_vkGetPhysicalDeviceWaylandPresentationSupportKHR vkGetPhysicalDeviceWaylandPresentationSupportKHR; +#endif /* defined(VK_KHR_wayland_surface) */ +#if defined(VK_KHR_win32_surface) +extern PFN_vkCreateWin32SurfaceKHR vkCreateWin32SurfaceKHR; +extern PFN_vkGetPhysicalDeviceWin32PresentationSupportKHR vkGetPhysicalDeviceWin32PresentationSupportKHR; +#endif /* defined(VK_KHR_win32_surface) */ +#if defined(VK_KHR_xcb_surface) +extern PFN_vkCreateXcbSurfaceKHR vkCreateXcbSurfaceKHR; +extern PFN_vkGetPhysicalDeviceXcbPresentationSupportKHR vkGetPhysicalDeviceXcbPresentationSupportKHR; +#endif /* defined(VK_KHR_xcb_surface) */ +#if defined(VK_KHR_xlib_surface) +extern PFN_vkCreateXlibSurfaceKHR vkCreateXlibSurfaceKHR; +extern PFN_vkGetPhysicalDeviceXlibPresentationSupportKHR vkGetPhysicalDeviceXlibPresentationSupportKHR; +#endif /* defined(VK_KHR_xlib_surface) */ +#if defined(VK_MVK_ios_surface) +extern PFN_vkCreateIOSSurfaceMVK vkCreateIOSSurfaceMVK; +#endif /* defined(VK_MVK_ios_surface) */ +#if defined(VK_MVK_macos_surface) +extern PFN_vkCreateMacOSSurfaceMVK vkCreateMacOSSurfaceMVK; +#endif /* defined(VK_MVK_macos_surface) */ +#if defined(VK_NN_vi_surface) +extern PFN_vkCreateViSurfaceNN vkCreateViSurfaceNN; +#endif /* defined(VK_NN_vi_surface) */ +#if defined(VK_NVX_binary_import) +extern PFN_vkCmdCuLaunchKernelNVX vkCmdCuLaunchKernelNVX; +extern PFN_vkCreateCuFunctionNVX vkCreateCuFunctionNVX; +extern PFN_vkCreateCuModuleNVX vkCreateCuModuleNVX; +extern PFN_vkDestroyCuFunctionNVX vkDestroyCuFunctionNVX; +extern PFN_vkDestroyCuModuleNVX vkDestroyCuModuleNVX; +#endif /* defined(VK_NVX_binary_import) */ +#if defined(VK_NVX_image_view_handle) +extern PFN_vkGetImageViewHandleNVX vkGetImageViewHandleNVX; +#endif /* defined(VK_NVX_image_view_handle) */ +#if defined(VK_NVX_image_view_handle) && VK_NVX_IMAGE_VIEW_HANDLE_SPEC_VERSION >= 3 +extern PFN_vkGetImageViewHandle64NVX vkGetImageViewHandle64NVX; +#endif /* defined(VK_NVX_image_view_handle) && VK_NVX_IMAGE_VIEW_HANDLE_SPEC_VERSION >= 3 */ +#if defined(VK_NVX_image_view_handle) && VK_NVX_IMAGE_VIEW_HANDLE_SPEC_VERSION >= 2 +extern PFN_vkGetImageViewAddressNVX vkGetImageViewAddressNVX; +#endif /* defined(VK_NVX_image_view_handle) && VK_NVX_IMAGE_VIEW_HANDLE_SPEC_VERSION >= 2 */ +#if defined(VK_NV_acquire_winrt_display) +extern PFN_vkAcquireWinrtDisplayNV vkAcquireWinrtDisplayNV; +extern PFN_vkGetWinrtDisplayNV vkGetWinrtDisplayNV; +#endif /* defined(VK_NV_acquire_winrt_display) */ +#if defined(VK_NV_clip_space_w_scaling) +extern PFN_vkCmdSetViewportWScalingNV vkCmdSetViewportWScalingNV; +#endif /* defined(VK_NV_clip_space_w_scaling) */ +#if defined(VK_NV_cooperative_matrix) +extern PFN_vkGetPhysicalDeviceCooperativeMatrixPropertiesNV vkGetPhysicalDeviceCooperativeMatrixPropertiesNV; +#endif /* defined(VK_NV_cooperative_matrix) */ +#if defined(VK_NV_cooperative_matrix2) +extern PFN_vkGetPhysicalDeviceCooperativeMatrixFlexibleDimensionsPropertiesNV vkGetPhysicalDeviceCooperativeMatrixFlexibleDimensionsPropertiesNV; +#endif /* defined(VK_NV_cooperative_matrix2) */ +#if defined(VK_NV_copy_memory_indirect) +extern PFN_vkCmdCopyMemoryIndirectNV vkCmdCopyMemoryIndirectNV; +extern PFN_vkCmdCopyMemoryToImageIndirectNV vkCmdCopyMemoryToImageIndirectNV; +#endif /* defined(VK_NV_copy_memory_indirect) */ +#if defined(VK_NV_coverage_reduction_mode) +extern PFN_vkGetPhysicalDeviceSupportedFramebufferMixedSamplesCombinationsNV vkGetPhysicalDeviceSupportedFramebufferMixedSamplesCombinationsNV; +#endif /* defined(VK_NV_coverage_reduction_mode) */ +#if defined(VK_NV_cuda_kernel_launch) +extern PFN_vkCmdCudaLaunchKernelNV vkCmdCudaLaunchKernelNV; +extern PFN_vkCreateCudaFunctionNV vkCreateCudaFunctionNV; +extern PFN_vkCreateCudaModuleNV vkCreateCudaModuleNV; +extern PFN_vkDestroyCudaFunctionNV vkDestroyCudaFunctionNV; +extern PFN_vkDestroyCudaModuleNV vkDestroyCudaModuleNV; +extern PFN_vkGetCudaModuleCacheNV vkGetCudaModuleCacheNV; +#endif /* defined(VK_NV_cuda_kernel_launch) */ +#if defined(VK_NV_device_diagnostic_checkpoints) +extern PFN_vkCmdSetCheckpointNV vkCmdSetCheckpointNV; +extern PFN_vkGetQueueCheckpointDataNV vkGetQueueCheckpointDataNV; +#endif /* defined(VK_NV_device_diagnostic_checkpoints) */ +#if defined(VK_NV_device_diagnostic_checkpoints) && (defined(VK_VERSION_1_3) || defined(VK_KHR_synchronization2)) +extern PFN_vkGetQueueCheckpointData2NV vkGetQueueCheckpointData2NV; +#endif /* defined(VK_NV_device_diagnostic_checkpoints) && (defined(VK_VERSION_1_3) || defined(VK_KHR_synchronization2)) */ +#if defined(VK_NV_device_generated_commands) +extern PFN_vkCmdBindPipelineShaderGroupNV vkCmdBindPipelineShaderGroupNV; +extern PFN_vkCmdExecuteGeneratedCommandsNV vkCmdExecuteGeneratedCommandsNV; +extern PFN_vkCmdPreprocessGeneratedCommandsNV vkCmdPreprocessGeneratedCommandsNV; +extern PFN_vkCreateIndirectCommandsLayoutNV vkCreateIndirectCommandsLayoutNV; +extern PFN_vkDestroyIndirectCommandsLayoutNV vkDestroyIndirectCommandsLayoutNV; +extern PFN_vkGetGeneratedCommandsMemoryRequirementsNV vkGetGeneratedCommandsMemoryRequirementsNV; +#endif /* defined(VK_NV_device_generated_commands) */ +#if defined(VK_NV_device_generated_commands_compute) +extern PFN_vkCmdUpdatePipelineIndirectBufferNV vkCmdUpdatePipelineIndirectBufferNV; +extern PFN_vkGetPipelineIndirectDeviceAddressNV vkGetPipelineIndirectDeviceAddressNV; +extern PFN_vkGetPipelineIndirectMemoryRequirementsNV vkGetPipelineIndirectMemoryRequirementsNV; +#endif /* defined(VK_NV_device_generated_commands_compute) */ +#if defined(VK_NV_external_memory_capabilities) +extern PFN_vkGetPhysicalDeviceExternalImageFormatPropertiesNV vkGetPhysicalDeviceExternalImageFormatPropertiesNV; +#endif /* defined(VK_NV_external_memory_capabilities) */ +#if defined(VK_NV_external_memory_rdma) +extern PFN_vkGetMemoryRemoteAddressNV vkGetMemoryRemoteAddressNV; +#endif /* defined(VK_NV_external_memory_rdma) */ +#if defined(VK_NV_external_memory_win32) +extern PFN_vkGetMemoryWin32HandleNV vkGetMemoryWin32HandleNV; +#endif /* defined(VK_NV_external_memory_win32) */ +#if defined(VK_NV_fragment_shading_rate_enums) +extern PFN_vkCmdSetFragmentShadingRateEnumNV vkCmdSetFragmentShadingRateEnumNV; +#endif /* defined(VK_NV_fragment_shading_rate_enums) */ +#if defined(VK_NV_low_latency2) +extern PFN_vkGetLatencyTimingsNV vkGetLatencyTimingsNV; +extern PFN_vkLatencySleepNV vkLatencySleepNV; +extern PFN_vkQueueNotifyOutOfBandNV vkQueueNotifyOutOfBandNV; +extern PFN_vkSetLatencyMarkerNV vkSetLatencyMarkerNV; +extern PFN_vkSetLatencySleepModeNV vkSetLatencySleepModeNV; +#endif /* defined(VK_NV_low_latency2) */ +#if defined(VK_NV_memory_decompression) +extern PFN_vkCmdDecompressMemoryIndirectCountNV vkCmdDecompressMemoryIndirectCountNV; +extern PFN_vkCmdDecompressMemoryNV vkCmdDecompressMemoryNV; +#endif /* defined(VK_NV_memory_decompression) */ +#if defined(VK_NV_mesh_shader) +extern PFN_vkCmdDrawMeshTasksIndirectNV vkCmdDrawMeshTasksIndirectNV; +extern PFN_vkCmdDrawMeshTasksNV vkCmdDrawMeshTasksNV; +#endif /* defined(VK_NV_mesh_shader) */ +#if defined(VK_NV_mesh_shader) && (defined(VK_KHR_draw_indirect_count) || defined(VK_VERSION_1_2)) +extern PFN_vkCmdDrawMeshTasksIndirectCountNV vkCmdDrawMeshTasksIndirectCountNV; +#endif /* defined(VK_NV_mesh_shader) && (defined(VK_KHR_draw_indirect_count) || defined(VK_VERSION_1_2)) */ +#if defined(VK_NV_optical_flow) +extern PFN_vkBindOpticalFlowSessionImageNV vkBindOpticalFlowSessionImageNV; +extern PFN_vkCmdOpticalFlowExecuteNV vkCmdOpticalFlowExecuteNV; +extern PFN_vkCreateOpticalFlowSessionNV vkCreateOpticalFlowSessionNV; +extern PFN_vkDestroyOpticalFlowSessionNV vkDestroyOpticalFlowSessionNV; +extern PFN_vkGetPhysicalDeviceOpticalFlowImageFormatsNV vkGetPhysicalDeviceOpticalFlowImageFormatsNV; +#endif /* defined(VK_NV_optical_flow) */ +#if defined(VK_NV_ray_tracing) +extern PFN_vkBindAccelerationStructureMemoryNV vkBindAccelerationStructureMemoryNV; +extern PFN_vkCmdBuildAccelerationStructureNV vkCmdBuildAccelerationStructureNV; +extern PFN_vkCmdCopyAccelerationStructureNV vkCmdCopyAccelerationStructureNV; +extern PFN_vkCmdTraceRaysNV vkCmdTraceRaysNV; +extern PFN_vkCmdWriteAccelerationStructuresPropertiesNV vkCmdWriteAccelerationStructuresPropertiesNV; +extern PFN_vkCompileDeferredNV vkCompileDeferredNV; +extern PFN_vkCreateAccelerationStructureNV vkCreateAccelerationStructureNV; +extern PFN_vkCreateRayTracingPipelinesNV vkCreateRayTracingPipelinesNV; +extern PFN_vkDestroyAccelerationStructureNV vkDestroyAccelerationStructureNV; +extern PFN_vkGetAccelerationStructureHandleNV vkGetAccelerationStructureHandleNV; +extern PFN_vkGetAccelerationStructureMemoryRequirementsNV vkGetAccelerationStructureMemoryRequirementsNV; +extern PFN_vkGetRayTracingShaderGroupHandlesNV vkGetRayTracingShaderGroupHandlesNV; +#endif /* defined(VK_NV_ray_tracing) */ +#if defined(VK_NV_scissor_exclusive) && VK_NV_SCISSOR_EXCLUSIVE_SPEC_VERSION >= 2 +extern PFN_vkCmdSetExclusiveScissorEnableNV vkCmdSetExclusiveScissorEnableNV; +#endif /* defined(VK_NV_scissor_exclusive) && VK_NV_SCISSOR_EXCLUSIVE_SPEC_VERSION >= 2 */ +#if defined(VK_NV_scissor_exclusive) +extern PFN_vkCmdSetExclusiveScissorNV vkCmdSetExclusiveScissorNV; +#endif /* defined(VK_NV_scissor_exclusive) */ +#if defined(VK_NV_shading_rate_image) +extern PFN_vkCmdBindShadingRateImageNV vkCmdBindShadingRateImageNV; +extern PFN_vkCmdSetCoarseSampleOrderNV vkCmdSetCoarseSampleOrderNV; +extern PFN_vkCmdSetViewportShadingRatePaletteNV vkCmdSetViewportShadingRatePaletteNV; +#endif /* defined(VK_NV_shading_rate_image) */ +#if defined(VK_QCOM_tile_properties) +extern PFN_vkGetDynamicRenderingTilePropertiesQCOM vkGetDynamicRenderingTilePropertiesQCOM; +extern PFN_vkGetFramebufferTilePropertiesQCOM vkGetFramebufferTilePropertiesQCOM; +#endif /* defined(VK_QCOM_tile_properties) */ +#if defined(VK_QNX_external_memory_screen_buffer) +extern PFN_vkGetScreenBufferPropertiesQNX vkGetScreenBufferPropertiesQNX; +#endif /* defined(VK_QNX_external_memory_screen_buffer) */ +#if defined(VK_QNX_screen_surface) +extern PFN_vkCreateScreenSurfaceQNX vkCreateScreenSurfaceQNX; +extern PFN_vkGetPhysicalDeviceScreenPresentationSupportQNX vkGetPhysicalDeviceScreenPresentationSupportQNX; +#endif /* defined(VK_QNX_screen_surface) */ +#if defined(VK_VALVE_descriptor_set_host_mapping) +extern PFN_vkGetDescriptorSetHostMappingVALVE vkGetDescriptorSetHostMappingVALVE; +extern PFN_vkGetDescriptorSetLayoutHostMappingInfoVALVE vkGetDescriptorSetLayoutHostMappingInfoVALVE; +#endif /* defined(VK_VALVE_descriptor_set_host_mapping) */ +#if (defined(VK_EXT_depth_clamp_control)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_depth_clamp_control)) +extern PFN_vkCmdSetDepthClampRangeEXT vkCmdSetDepthClampRangeEXT; +#endif /* (defined(VK_EXT_depth_clamp_control)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_depth_clamp_control)) */ +#if (defined(VK_EXT_extended_dynamic_state)) || (defined(VK_EXT_shader_object)) +extern PFN_vkCmdBindVertexBuffers2EXT vkCmdBindVertexBuffers2EXT; +extern PFN_vkCmdSetCullModeEXT vkCmdSetCullModeEXT; +extern PFN_vkCmdSetDepthBoundsTestEnableEXT vkCmdSetDepthBoundsTestEnableEXT; +extern PFN_vkCmdSetDepthCompareOpEXT vkCmdSetDepthCompareOpEXT; +extern PFN_vkCmdSetDepthTestEnableEXT vkCmdSetDepthTestEnableEXT; +extern PFN_vkCmdSetDepthWriteEnableEXT vkCmdSetDepthWriteEnableEXT; +extern PFN_vkCmdSetFrontFaceEXT vkCmdSetFrontFaceEXT; +extern PFN_vkCmdSetPrimitiveTopologyEXT vkCmdSetPrimitiveTopologyEXT; +extern PFN_vkCmdSetScissorWithCountEXT vkCmdSetScissorWithCountEXT; +extern PFN_vkCmdSetStencilOpEXT vkCmdSetStencilOpEXT; +extern PFN_vkCmdSetStencilTestEnableEXT vkCmdSetStencilTestEnableEXT; +extern PFN_vkCmdSetViewportWithCountEXT vkCmdSetViewportWithCountEXT; +#endif /* (defined(VK_EXT_extended_dynamic_state)) || (defined(VK_EXT_shader_object)) */ +#if (defined(VK_EXT_extended_dynamic_state2)) || (defined(VK_EXT_shader_object)) +extern PFN_vkCmdSetDepthBiasEnableEXT vkCmdSetDepthBiasEnableEXT; +extern PFN_vkCmdSetLogicOpEXT vkCmdSetLogicOpEXT; +extern PFN_vkCmdSetPatchControlPointsEXT vkCmdSetPatchControlPointsEXT; +extern PFN_vkCmdSetPrimitiveRestartEnableEXT vkCmdSetPrimitiveRestartEnableEXT; +extern PFN_vkCmdSetRasterizerDiscardEnableEXT vkCmdSetRasterizerDiscardEnableEXT; +#endif /* (defined(VK_EXT_extended_dynamic_state2)) || (defined(VK_EXT_shader_object)) */ +#if (defined(VK_EXT_extended_dynamic_state3)) || (defined(VK_EXT_shader_object)) +extern PFN_vkCmdSetAlphaToCoverageEnableEXT vkCmdSetAlphaToCoverageEnableEXT; +extern PFN_vkCmdSetAlphaToOneEnableEXT vkCmdSetAlphaToOneEnableEXT; +extern PFN_vkCmdSetColorBlendEnableEXT vkCmdSetColorBlendEnableEXT; +extern PFN_vkCmdSetColorBlendEquationEXT vkCmdSetColorBlendEquationEXT; +extern PFN_vkCmdSetColorWriteMaskEXT vkCmdSetColorWriteMaskEXT; +extern PFN_vkCmdSetDepthClampEnableEXT vkCmdSetDepthClampEnableEXT; +extern PFN_vkCmdSetLogicOpEnableEXT vkCmdSetLogicOpEnableEXT; +extern PFN_vkCmdSetPolygonModeEXT vkCmdSetPolygonModeEXT; +extern PFN_vkCmdSetRasterizationSamplesEXT vkCmdSetRasterizationSamplesEXT; +extern PFN_vkCmdSetSampleMaskEXT vkCmdSetSampleMaskEXT; +#endif /* (defined(VK_EXT_extended_dynamic_state3)) || (defined(VK_EXT_shader_object)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && (defined(VK_KHR_maintenance2) || defined(VK_VERSION_1_1))) || (defined(VK_EXT_shader_object)) +extern PFN_vkCmdSetTessellationDomainOriginEXT vkCmdSetTessellationDomainOriginEXT; +#endif /* (defined(VK_EXT_extended_dynamic_state3) && (defined(VK_KHR_maintenance2) || defined(VK_VERSION_1_1))) || (defined(VK_EXT_shader_object)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_transform_feedback)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_transform_feedback)) +extern PFN_vkCmdSetRasterizationStreamEXT vkCmdSetRasterizationStreamEXT; +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_transform_feedback)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_transform_feedback)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_conservative_rasterization)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_conservative_rasterization)) +extern PFN_vkCmdSetConservativeRasterizationModeEXT vkCmdSetConservativeRasterizationModeEXT; +extern PFN_vkCmdSetExtraPrimitiveOverestimationSizeEXT vkCmdSetExtraPrimitiveOverestimationSizeEXT; +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_conservative_rasterization)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_conservative_rasterization)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_depth_clip_enable)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_depth_clip_enable)) +extern PFN_vkCmdSetDepthClipEnableEXT vkCmdSetDepthClipEnableEXT; +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_depth_clip_enable)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_depth_clip_enable)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_sample_locations)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_sample_locations)) +extern PFN_vkCmdSetSampleLocationsEnableEXT vkCmdSetSampleLocationsEnableEXT; +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_sample_locations)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_sample_locations)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_blend_operation_advanced)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_blend_operation_advanced)) +extern PFN_vkCmdSetColorBlendAdvancedEXT vkCmdSetColorBlendAdvancedEXT; +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_blend_operation_advanced)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_blend_operation_advanced)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_provoking_vertex)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_provoking_vertex)) +extern PFN_vkCmdSetProvokingVertexModeEXT vkCmdSetProvokingVertexModeEXT; +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_provoking_vertex)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_provoking_vertex)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_line_rasterization)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_line_rasterization)) +extern PFN_vkCmdSetLineRasterizationModeEXT vkCmdSetLineRasterizationModeEXT; +extern PFN_vkCmdSetLineStippleEnableEXT vkCmdSetLineStippleEnableEXT; +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_line_rasterization)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_line_rasterization)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_depth_clip_control)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_depth_clip_control)) +extern PFN_vkCmdSetDepthClipNegativeOneToOneEXT vkCmdSetDepthClipNegativeOneToOneEXT; +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_depth_clip_control)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_depth_clip_control)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_clip_space_w_scaling)) || (defined(VK_EXT_shader_object) && defined(VK_NV_clip_space_w_scaling)) +extern PFN_vkCmdSetViewportWScalingEnableNV vkCmdSetViewportWScalingEnableNV; +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_clip_space_w_scaling)) || (defined(VK_EXT_shader_object) && defined(VK_NV_clip_space_w_scaling)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_viewport_swizzle)) || (defined(VK_EXT_shader_object) && defined(VK_NV_viewport_swizzle)) +extern PFN_vkCmdSetViewportSwizzleNV vkCmdSetViewportSwizzleNV; +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_viewport_swizzle)) || (defined(VK_EXT_shader_object) && defined(VK_NV_viewport_swizzle)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_fragment_coverage_to_color)) || (defined(VK_EXT_shader_object) && defined(VK_NV_fragment_coverage_to_color)) +extern PFN_vkCmdSetCoverageToColorEnableNV vkCmdSetCoverageToColorEnableNV; +extern PFN_vkCmdSetCoverageToColorLocationNV vkCmdSetCoverageToColorLocationNV; +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_fragment_coverage_to_color)) || (defined(VK_EXT_shader_object) && defined(VK_NV_fragment_coverage_to_color)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_framebuffer_mixed_samples)) || (defined(VK_EXT_shader_object) && defined(VK_NV_framebuffer_mixed_samples)) +extern PFN_vkCmdSetCoverageModulationModeNV vkCmdSetCoverageModulationModeNV; +extern PFN_vkCmdSetCoverageModulationTableEnableNV vkCmdSetCoverageModulationTableEnableNV; +extern PFN_vkCmdSetCoverageModulationTableNV vkCmdSetCoverageModulationTableNV; +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_framebuffer_mixed_samples)) || (defined(VK_EXT_shader_object) && defined(VK_NV_framebuffer_mixed_samples)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_shading_rate_image)) || (defined(VK_EXT_shader_object) && defined(VK_NV_shading_rate_image)) +extern PFN_vkCmdSetShadingRateImageEnableNV vkCmdSetShadingRateImageEnableNV; +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_shading_rate_image)) || (defined(VK_EXT_shader_object) && defined(VK_NV_shading_rate_image)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_representative_fragment_test)) || (defined(VK_EXT_shader_object) && defined(VK_NV_representative_fragment_test)) +extern PFN_vkCmdSetRepresentativeFragmentTestEnableNV vkCmdSetRepresentativeFragmentTestEnableNV; +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_representative_fragment_test)) || (defined(VK_EXT_shader_object) && defined(VK_NV_representative_fragment_test)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_coverage_reduction_mode)) || (defined(VK_EXT_shader_object) && defined(VK_NV_coverage_reduction_mode)) +extern PFN_vkCmdSetCoverageReductionModeNV vkCmdSetCoverageReductionModeNV; +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_coverage_reduction_mode)) || (defined(VK_EXT_shader_object) && defined(VK_NV_coverage_reduction_mode)) */ +#if (defined(VK_EXT_host_image_copy)) || (defined(VK_EXT_image_compression_control)) +extern PFN_vkGetImageSubresourceLayout2EXT vkGetImageSubresourceLayout2EXT; +#endif /* (defined(VK_EXT_host_image_copy)) || (defined(VK_EXT_image_compression_control)) */ +#if (defined(VK_EXT_shader_object)) || (defined(VK_EXT_vertex_input_dynamic_state)) +extern PFN_vkCmdSetVertexInputEXT vkCmdSetVertexInputEXT; +#endif /* (defined(VK_EXT_shader_object)) || (defined(VK_EXT_vertex_input_dynamic_state)) */ +#if (defined(VK_KHR_descriptor_update_template) && defined(VK_KHR_push_descriptor)) || (defined(VK_KHR_push_descriptor) && (defined(VK_VERSION_1_1) || defined(VK_KHR_descriptor_update_template))) +extern PFN_vkCmdPushDescriptorSetWithTemplateKHR vkCmdPushDescriptorSetWithTemplateKHR; +#endif /* (defined(VK_KHR_descriptor_update_template) && defined(VK_KHR_push_descriptor)) || (defined(VK_KHR_push_descriptor) && (defined(VK_VERSION_1_1) || defined(VK_KHR_descriptor_update_template))) */ +#if (defined(VK_KHR_device_group) && defined(VK_KHR_surface)) || (defined(VK_KHR_swapchain) && defined(VK_VERSION_1_1)) +extern PFN_vkGetDeviceGroupPresentCapabilitiesKHR vkGetDeviceGroupPresentCapabilitiesKHR; +extern PFN_vkGetDeviceGroupSurfacePresentModesKHR vkGetDeviceGroupSurfacePresentModesKHR; +extern PFN_vkGetPhysicalDevicePresentRectanglesKHR vkGetPhysicalDevicePresentRectanglesKHR; +#endif /* (defined(VK_KHR_device_group) && defined(VK_KHR_surface)) || (defined(VK_KHR_swapchain) && defined(VK_VERSION_1_1)) */ +#if (defined(VK_KHR_device_group) && defined(VK_KHR_swapchain)) || (defined(VK_KHR_swapchain) && defined(VK_VERSION_1_1)) +extern PFN_vkAcquireNextImage2KHR vkAcquireNextImage2KHR; +#endif /* (defined(VK_KHR_device_group) && defined(VK_KHR_swapchain)) || (defined(VK_KHR_swapchain) && defined(VK_VERSION_1_1)) */ +/* VOLK_GENERATE_PROTOTYPES_H */ + +#ifdef __cplusplus +} +#endif + +#endif + +#ifdef VOLK_IMPLEMENTATION +#undef VOLK_IMPLEMENTATION +/* Prevent tools like dependency checkers from detecting a cyclic dependency */ +#define VOLK_SOURCE "volk.c" +#include VOLK_SOURCE +#endif + +/** + * Copyright (c) 2018-2024 Arseny Kapoulkine + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in all + * copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. +*/ +/* clang-format on */ diff --git a/include/fennec/platform/window_manager.h b/include/fennec/platform/window_manager.h index affbe22..354efe7 100644 --- a/include/fennec/platform/window_manager.h +++ b/include/fennec/platform/window_manager.h @@ -104,12 +104,13 @@ public: /// \brief destructor ~window_manager(); - /// @} - - -private: + /// + /// \brief Copy Constructor + /// \details Deleted, no semantics for copying a platform window_manager(const window_manager&) = delete; + /// @} + // Initialization & Update ============================================================================================= public: @@ -247,7 +248,7 @@ public: /// \brief tests if the window is visible /// /// \param window The window. - /// \returns \f$true\f$ if the window is visible, \f$false\f$ otherwise + /// \returns \emph{true} if the window is visible, \emph{false} otherwise bool is_visible(window_id window) const { lock_guard guard(_lock); return _check_state(window, window::state_visible); @@ -257,7 +258,7 @@ public: /// \brief tests if the window is a child /// /// \param window The window. - /// \returns \f$true\f$ if the window is a child, \f$false\f$ otherwise + /// \returns \emph{true} if the window is a child, \emph{false} otherwise bool is_child(window_id window) const { lock_guard guard(_lock); return _check_state(window, window::state_child); @@ -267,7 +268,7 @@ public: /// \brief tests if the window is running /// /// \param window The window. - /// \returns \f$true\f$ if the window is running, \f$false\f$ otherwise + /// \returns \emph{true} if the window is running, \emph{false} otherwise bool is_running(window_id window) const { lock_guard guard(_lock); return _check_state(window, window::state_running); @@ -277,7 +278,7 @@ public: /// \brief tests if the window is suspended /// /// \param window The window. - /// \returns \f$true\f$ if the window is suspended, \f$false\f$ otherwise + /// \returns \emph{true} if the window is suspended, \emph{false} otherwise bool is_suspended(window_id window) const { lock_guard guard(_lock); return _check_state(window, window::state_suspended); @@ -297,7 +298,7 @@ public: /// /// \param window The window. /// \param flag the flag from `window::flag_` - /// \returns \f$true\f$ if the flag is set, \f$false\f$ otherwise + /// \returns \emph{true} if the flag is set, \emph{false} otherwise bool get_flag(window_id window, uint8_t flag) { lock_guard guard(_lock); return _get_flag(window, flag); @@ -308,7 +309,7 @@ public: /// \brief check if the window is flagged to always be on top of other windows /// /// \param window The window. - /// \returns \f$true\f$ if set, \f$false\f$ otherwise + /// \returns \emph{true} if set, \emph{false} otherwise bool is_always_on_top(window_id window) { return get_flag(window, window::flag_always_on_top); } @@ -317,7 +318,7 @@ public: /// \brief check if the window is flagged to have no window decorations /// /// \param window The window. - /// \returns \f$true\f$ if set, \f$false\f$ otherwise + /// \returns \emph{true} if set, \emph{false} otherwise bool is_borderless(window_id window) { return get_flag(window, window::flag_borderless); } @@ -326,7 +327,7 @@ public: /// \brief check if the window is flagged to be modal /// /// \param window The window. - /// \returns \f$true\f$ if set, \f$false\f$ otherwise + /// \returns \emph{true} if set, \emph{false} otherwise bool is_modal(window_id window) { return get_flag(window, window::flag_modal); } @@ -335,7 +336,7 @@ public: /// \brief check if the window is flagged to pass mouse input to windows underneath from the same application /// /// \param window The window. - /// \returns \f$true\f$ if set, \f$false\f$ otherwise + /// \returns \emph{true} if set, \emph{false} otherwise bool is_passing_mouse(window_id window) { return get_flag(window, window::flag_pass_mouse); } @@ -344,7 +345,7 @@ public: /// \brief check if the window is flagged as a popup /// /// \param window The window. - /// \returns \f$true\f$ if set, \f$false\f$ otherwise + /// \returns \emph{true} if set, \emph{false} otherwise bool is_popup(window_id window) { return get_flag(window, window::flag_popup); } @@ -353,7 +354,7 @@ public: /// \brief check if the window is flagged to be resizable /// /// \param window The window. - /// \returns \f$true\f$ if set, \f$false\f$ otherwise + /// \returns \emph{true} if set, \emph{false} otherwise bool is_resizable(window_id window) { return get_flag(window, window::flag_resizable); } @@ -362,7 +363,7 @@ public: /// \brief check if the window is flagged to be transparent /// /// \param window The window. - /// \returns \f$true\f$ if set, \f$false\f$ otherwise + /// \returns \emph{true} if set, \emph{false} otherwise bool is_transparent(window_id window) { return get_flag(window, window::flag_transparent); } @@ -371,7 +372,7 @@ public: /// \brief check if the window is flagged to be unfocusable /// /// \param window The window. - /// \returns \f$true\f$ if set, \f$false\f$ otherwise + /// \returns \emph{true} if set, \emph{false} otherwise bool is_no_focus(window_id window) { return get_flag(window, window::flag_no_focus); } @@ -398,7 +399,6 @@ public: /// /// \param window The window. /// \param val the value to set the flag to - /// \returns \f$true\f$ on success, \f$false\f$ otherwise void set_always_on_top(window_id window, bool val) { return set_flag(window, window::flag_always_on_top, val); } @@ -408,7 +408,6 @@ public: /// /// \param window The window. /// \param val the value to set the flag to - /// \returns \f$true\f$ on success, \f$false\f$ otherwise void set_borderless(window_id window, bool val) { return set_flag(window, window::flag_borderless, val); } @@ -418,7 +417,6 @@ public: /// /// \param window The window. /// \param val the value to set the flag to - /// \returns \f$true\f$ on success, \f$false\f$ otherwise void set_modal(window_id window, bool val) { return set_flag(window, window::flag_modal, val); } @@ -428,7 +426,6 @@ public: /// /// \param window The window. /// \param val the value to set the flag to - /// \returns \f$true\f$ on success, \f$false\f$ otherwise void set_passing_mouse(window_id window, bool val) { return set_flag(window, window::flag_pass_mouse, val); } @@ -438,7 +435,6 @@ public: /// /// \param window The window. /// \param val the value to set the flag to - /// \returns \f$true\f$ on success, \f$false\f$ otherwise void set_popup(window_id window, bool val) { return set_flag(window, window::flag_popup, val); } @@ -448,7 +444,6 @@ public: /// /// \param window The window. /// \param val the value to set the flag to - /// \returns \f$true\f$ on success, \f$false\f$ otherwise void set_resizable(window_id window, bool val) { return set_flag(window, window::flag_resizable, val); } @@ -458,7 +453,6 @@ public: /// /// \param window The window. /// \param val the value to set the flag to - /// \returns \f$true\f$ on success, \f$false\f$ otherwise void set_transparent(window_id window, bool val) { return set_flag(window, window::flag_transparent, val); } @@ -468,7 +462,6 @@ public: /// /// \param window The window. /// \param val the value to set the flag to - /// \returns \f$true\f$ on success, \f$false\f$ otherwise void set_no_focus(window_id window, bool val) { return set_flag(window, window::flag_no_focus, val); } diff --git a/include/fennec/renderers/interface/gfxcontext.h b/include/fennec/renderers/interface/gfxcontext.h index 9fb8c2c..7dce84d 100644 --- a/include/fennec/renderers/interface/gfxcontext.h +++ b/include/fennec/renderers/interface/gfxcontext.h @@ -76,12 +76,15 @@ public: /// @{ /// - /// \returns \f$true\f$ if this + /// \brief Context Validity + /// \returns \emph{true} if the context is initialized and valid, \emph{false} otherwise. virtual bool is_valid() = 0; /// /// \returns A version struct containing the version of the graphics API. - virtual const version& get_version() const { return version; } + virtual const version& get_version() const { + return version; + } /// @} @@ -108,12 +111,6 @@ protected: FENNEC_RTTI_CLASS_ENABLE() { } - - -// Assignment Operators ================================================================================================ -private: - gfxcontext& operator=(const gfxcontext&) = delete; - gfxcontext& operator=(gfxcontext&&) = delete; }; } diff --git a/include/fennec/renderers/opengl/lib/buffer.h b/include/fennec/renderers/opengl/lib/buffer.h deleted file mode 100644 index 79a769b..0000000 --- a/include/fennec/renderers/opengl/lib/buffer.h +++ /dev/null @@ -1,536 +0,0 @@ -// ===================================================================================================================== -// fennec, a free and open source game engine -// Copyright © 2025 - 2026 Medusa Slockbower -// -// This program is free software: you can redistribute it and/or modify -// it under the terms of the GNU General Public License as published by -// the Free Software Foundation, either version 3 of the License, or -// (at your option) any later version. -// -// This program is distributed in the hope that it will be useful, -// but WITHOUT ANY WARRANTY; without even the implied warranty of -// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -// GNU General Public License for more details. -// -// You should have received a copy of the GNU General Public License -// along with this program. If not, see . -// ===================================================================================================================== - -/// -/// \file fennec/renderers/opengl/lib/buffer.h -/// \brief -/// -/// -/// \details -/// \author Medusa Slockbower -/// -/// \copyright Copyright © 2025 - 2026 Medusa Slockbower ([GPLv3](https://www.gnu.org/licenses/gpl-3.0.en.html)) -/// -/// - -#ifndef FENNEC_RENDERERS_OPENGL_LIB_BUFFER_H -#define FENNEC_RENDERERS_OPENGL_LIB_BUFFER_H - -#include - -#include -#include - -namespace fennec -{ - -namespace gl -{ - -/// -/// \brief Vertex Buffer Alias -/// \tparam FlagsV The buffer flags, see \ref fennec::gl::buffer_map_flags "buffer_map_flags" -/// \tparam ImmutableV Mutability -template -using vertex_buffer = buffer; - -/// -/// \brief Vertex Buffer Alias -/// \tparam FlagsV The buffer flags, see \ref fennec::gl::buffer_map_flags "buffer_map_flags" -/// \tparam ImmutableV Mutability -template -using element_buffer = buffer; - -/// -/// \brief Vertex Buffer Alias -/// \tparam FlagsV The buffer flags, see \ref fennec::gl::buffer_map_flags "buffer_map_flags" -/// \tparam ImmutableV Mutability -template -using uniform_buffer = buffer; - -/// -/// \brief Vertex Buffer Alias -/// \tparam FlagsV The buffer flags, see \ref fennec::gl::buffer_map_flags "buffer_map_flags" -/// \tparam ImmutableV Mutability -template -using shader_storage_buffer = buffer; - -/// -/// \brief Vertex Buffer Alias -/// \tparam FlagsV The buffer flags, see \ref fennec::gl::buffer_map_flags "buffer_map_flags" -/// \tparam ImmutableV Mutability -template -using query_buffer = buffer; - -/// -/// \brief Vertex Buffer Alias -/// \tparam FlagsV The buffer flags, see \ref fennec::gl::buffer_map_flags "buffer_map_flags" -/// \tparam ImmutableV Mutability -template -using texture_buffer = buffer; - -/// -/// \brief Vertex Buffer Alias -/// \tparam FlagsV The buffer flags, see \ref fennec::gl::buffer_map_flags "buffer_map_flags" -/// \tparam ImmutableV Mutability -template -using transform_feedback_buffer = buffer; - -/// -/// \brief Vertex Buffer Alias -/// \tparam FlagsV The buffer flags, see \ref fennec::gl::buffer_map_flags "buffer_map_flags" -/// \tparam ImmutableV Mutability -template -using atomic_counter_buffer = buffer; - -/// -/// \brief Vertex Buffer Alias -/// \tparam FlagsV The buffer flags, see \ref fennec::gl::buffer_map_flags "buffer_map_flags" -/// \tparam ImmutableV Mutability -template -using parameter_buffer = buffer; - -/// -/// \brief Vertex Buffer Alias -/// \tparam FlagsV The buffer flags, see \ref fennec::gl::buffer_map_flags "buffer_map_flags" -/// \tparam ImmutableV Mutability -template -using indirect_draw_buffer = buffer; - -/// -/// \brief Vertex Buffer Alias -/// \tparam FlagsV The buffer flags, see \ref fennec::gl::buffer_map_flags "buffer_map_flags" -/// \tparam ImmutableV Mutability -template -using indirect_dispatch_buffer = buffer; - -/// -/// \brief Vertex Buffer Alias -/// \tparam FlagsV The buffer flags, see \ref fennec::gl::buffer_map_flags "buffer_map_flags" -/// \tparam ImmutableV Mutability -template -using copy_read_buffer = buffer; - -/// -/// \brief Vertex Buffer Alias -/// \tparam FlagsV The buffer flags, see \ref fennec::gl::buffer_map_flags "buffer_map_flags" -/// \tparam ImmutableV Mutability -template -using copy_write_buffer = buffer; - -/// -/// \brief Vertex Buffer Alias -/// \tparam FlagsV The buffer flags, see \ref fennec::gl::buffer_map_flags "buffer_map_flags" -/// \tparam ImmutableV Mutability -template -using pixel_pack_buffer = buffer; - -/// -/// \brief Vertex Buffer Alias -/// \tparam FlagsV The buffer flags, see \ref fennec::gl::buffer_map_flags "buffer_map_flags" -/// \tparam ImmutableV Mutability -template -using pixel_unpack_buffer = buffer; - -/// -/// \brief -/// \tparam TypeV The buffer type, see \ref fennec::gl::buffer_types "buffer_types" -/// \tparam FlagsV The buffer flags, see \ref fennec::gl::buffer_map_flags "buffer_map_flags" -/// \tparam ImmutableV Mutability -template -class buffer { - -// Private Helpers ===================================================================================================== -private: - static constexpr GLenum get_mutable_traits() { - GLenum res; - - // Set READ/DRAW/COPY - if constexpr (map_read) { - res = GL_STREAM_READ; - } else if constexpr (map_write) { - res = GL_STREAM_DRAW; - } else { - res = GL_STREAM_COPY; - } - - // Set STATIC/DYNAMIC/STREAM - if constexpr (client or coherent) { - // do nothing - } else if constexpr (dynamic or persistent) { - res += 6; - } else { - res += 3; - } - - return res; - } - - -// Constants =========================================================================================================== -public: - - /// \name Constants - /// @{ - - /// - /// \brief Enum value containing the buffer type. - /// \see fennec::gl::buffer_types - static constexpr GLenum type = TypeV; - - /// - /// \brief Boolean value representing whether this buffer is immutable. - /// \note Immutable buffers may not be resized. - static constexpr GLboolean immutable = ImmutableV; - - /// - /// \brief Bitfield value containing the buffer flags. - /// \see fennec::gl::buffer_map_flags - static constexpr GLbitfield flags = FlagsV; - - /// - /// \brief Boolean value representing whether this buffer has indexed binding targets. - /// \note Indexed buffer types must be bound to an indexed binding target to be used in shaders. - /// \see fennec::gl::buffer::bind - /// \see fennec::gl::buffer::bind_range - static constexpr GLboolean indexed = type == ATOMIC_COUNTER or type == SHADER_STORAGE or type == TRANSFORM_FEEDBACK or type == UNIFORM; - - /// - /// \brief Boolean value representing whether this buffer is mapped for reading. - /// \note Not to be confused with `read()`, which is specifically for dynamic buffers. - /// \see fennec::gl::buffer::map - static constexpr GLboolean map_read = flags & READ; - - /// - /// \brief Boolean value representing whether this buffer is mapped for writing. - /// \note Not to be confused with `write()`, which is specifically for dynamic buffers. - /// \see fennec::gl::buffer::map - static constexpr GLboolean map_write = flags & WRITE; - - /// - /// \brief Boolean value representing whether this buffer is mapped - /// \see fennec::gl::buffer::map - static constexpr GLboolean mapped = map_read or map_write; - - /// - /// \brief Boolean value representing whether this buffer is dynamic. - /// \note This allows use of the dynamic `read()` and `write()` functions. - /// \see fennec::gl::buffer::read - /// \see fennec::gl::buffer::write - static constexpr GLboolean dynamic = flags & DYNAMIC; - - /// - /// \brief Boolean value representing whether this buffer is persistent, i.e. can be used while mapped. - /// \see fennec::gl::buffer::map - static constexpr GLboolean persistent = flags & PERSISTENT; - - /// - /// \brief Boolean value representing whether this buffer is coherent when mapped. - /// \see fennec::gl::buffer::map - static constexpr GLboolean coherent = flags & COHERENT; - - /// - /// \brief Boolean value representing whether this buffers memory is on the client. - /// \note This is only a hint for the driver, which may be ignored. - static constexpr GLboolean client = flags & CLIENT; - - /// - /// \brief Enum value containing the mutable usage traits. - /// \see fennec::gl::buffer::immutable - static constexpr GLenum usage = get_mutable_traits(); - - /// @} - - -// Assertions ========================================================================================================== -public: - - static_assert(not persistent or persistent == mapped, "Persistent buffer must be mappable."); - static_assert(not coherent or coherent == persistent, "Coherent buffer must be persistent."); - - -// Constructors & Destructor =========================================================================================== -public: - - /// \name Constructors & Destructor - /// @{ - - /// - /// \brief Buffer Data Constructor - /// \param data Data to upload to the buffer, may be \f$nullptr\f$. - /// \param size Size of the buffer. - buffer(const void* data, GLsizeiptr size) - : _handle() - , _size(size) - , _data(nullptr) - , _mapflags(0) { - glGenBuffers(1, &_handle); - use(); - if constexpr(immutable) { - glBufferStorage(type, _size, data, flags); - } else { - glBufferData(type, _size, data, usage); - } - } - - /// - /// \brief Buffer Move Constructor - /// \param buff The buffer to take ownership of - buffer(buffer&& buff) noexcept - : _handle(buff) - , _size(buff._size) - , _data(nullptr) - , _mapflags(0) { - } - - /// - /// \brief Buffer Destructor - /// - /// \details Cleans up buffer data and object - ~buffer() { - glDeleteBuffers(1, &_handle); - } - - /// @} - -private: - buffer(const buffer&) = delete; - - -// Assignment ========================================================================================================== -public: - - /// \name Assignment - /// @{ - - /// - /// \brief Buffer Move Assignment - /// \param buff The buffer to take ownership of. - /// \returns A reference to self after having taken ownership of \f$buff\f$. - buffer& operator=(buffer&& buff) noexcept { - fennec::swap(_handle, buff._handle); - fennec::swap(_size, buff._size); - return *this; - } - - /// @} - - -private: - buffer& operator=(const buffer&) = delete; - - -// Use & Binding ======================================================================================================= -public: - - /// \name Use & Binding - /// @{ - - /// - /// \brief Use this buffer for buffer operations. - void use() const { - glBindBuffer(type, _handle); - } - - /// - /// \brief Bind this buffer to an indexed target. - /// - /// \param i The index to bind to. - /// \see fennec::gl::buffer::type. - void bind(GLuint i) { - static_assert(indexed, "Buffer must have an indexed binding target."); - - glBindBufferBase(type, i, _handle); - } - - /// - /// \brief Bind a range of this buffer to an indexed target. - /// \param i The index to bind to. - /// \param size The size of the range to bind. - /// \param offset The offset of the range to bind. - void bind_range(GLuint i, GLsizeiptr size = -1, GLintptr offset = 0) { - static_assert(indexed, "Buffer must have an indexed binding target."); - - offset = max(offset, GLintptr(0)); - size = size < 0 ? _size : size; - size = min(size, _size - offset); - if (size <= 0) return; - glBindBufferRange(type, i, _handle, offset, size); - } - - /// @} - - -// Mapping ============================================================================================================= -public: - /// \name Mapping - /// @{ - - /// - /// \brief Map a range of the buffer to be used by the client. - /// \param access The access specifiers. - /// \param size The size of the range to map. - /// \param offset The offset of the range to map. - /// \return - void* map(GLbitfield access, GLsizeiptr size = -1, GLintptr offset = 0) { - if (_data) { - return _data; - } - - offset = max(offset, GLintptr(0)); - size = size < 0 ? _size : size; - size = min(size, _size - offset); - if (size <= 0) return nullptr; - return _data = glMapBufferRange(type, offset, size, _mapflags = flags | access); - } - - /// - /// \brief Release the mapping of the buffer. - void unmap() { - glUnmapBuffer(type); - _data = nullptr; - } - - /// @} - - -// Operations ========================================================================================================== -public: - - /// - /// \brief Resize the buffer. - /// - /// \param size The new size for the buffer. - /// \note Buffer must be mutable. Clears buffer with zeroes. - /// \see fennec::gl::buffer::immutable - void resize(GLsizei size) requires(not immutable) { - unmap(); - glBufferData(type, _size = size, nullptr, usage); - } - - /// - /// \brief Clear the buffer. - /// \param size The number of elements to clear - /// \param offset The offset into the buffer to begin clearing. - /// \param value The value to clear with. Must be a pointer to an object of appropriate size for the type and format. - /// \param value_type The type of the data. - /// \param format The format of the data. - /// \param internal The assumed internal format of the buffer. - void clear(GLsizeiptr size = -1, GLintptr offset = 0, const void* value = nullptr, GLenum value_type = BYTE, GLenum format = R, GLenum internal = R8) { - offset = max(offset, GLintptr(0)); - size = size < 0 ? _size : size; - size = min(size, _size - offset); - if (size <= 0) return; - glClearBufferSubData(type, internal, offset, size, format, value_type, value); - } - - /// - /// \brief Copy data from another buffer. - /// \tparam OTypeV The type of the buffer to copy from. - /// \tparam OFlagsV The flags of the buffer being copied from. - /// \tparam OImmutableV The mutability of the buffer being copied from. - /// \param cpy The buffer to copy. - /// \param size The size of the region to copy - /// \param write_offset The offset into this buffer to begin writing at. - /// \param read_offset The offset into \f$cpy\f$ to begin reading from. - template - void copy(const buffer& cpy, GLsizeiptr size = -1, GLintptr write_offset = 0, GLintptr read_offset = 0) { - write_offset = max(write_offset, GLintptr(0)); - read_offset = max(read_offset, GLintptr(0)); - size = size < 0 ? _size : size; - size = fennec::min(size, cpy._size - read_offset); - size = fennec::min(size, _size - write_offset); - if (size <= 0) return; - glBindBuffer(COPY_READ, cpy._handle); - glBindBuffer(COPY_WRITE, _handle); - glCopyBufferSubData(COPY_READ, COPY_WRITE, read_offset, write_offset, size); - glBindBuffer(COPY_READ, NULL); - glBindBuffer(COPY_WRITE, NULL); - } - - /// - /// \brief Read data from the buffer. - /// \param data The handle to the client buffer to read into. - /// \param size The size of the region to read. - /// \param offset The offset into the buffer to begin reading from. - void read(void* data, GLsizeiptr size, GLintptr offset = 0) const { - static_assert(dynamic); - offset = max(offset, GLintptr(0)); - size = size < 0 ? _size : size; - size = min(size, _size - offset); - if (size <= 0) return; - glGetBufferSubData(type, offset, size, data); - } - - /// - /// \brief Write data to the buffer. - /// \param data The handle to the client buffer to write from. - /// \param size The size of the region to write. - /// \param offset The offset into the buffer to begin writing at. - void write(const void* data, GLsizeiptr size, GLintptr offset = 0) { - static_assert(dynamic); - offset = max(offset, GLintptr(0)); - size = size < 0 ? _size : size; - size = min(size, _size - offset); - if (size <= 0) return; - glBufferSubData(type, offset, size, data); - } - - /// - /// \brief Flush a range of the buffer. - /// \param size The size of the range. - /// \param offset The offset of the range. - /// \note The buffer must be mapped with the \ref fennec::gl::buffer_map_flags::EXPLICIT_FLUSH "EXPLICIT_FLUSH" flag. - void flush(GLsizeiptr size = -1, GLintptr offset = 0) { - if (not _data) return; - if (not (_mapflags & EXPLICIT_FLUSH)) return; - offset = max(offset, GLintptr(0)); - size = size < 0 ? _size : size; - size = min(size, _size - offset); - if (size <= 0) return; - glFlushMappedBufferRange(type, offset, size); - } - - void invalidate(GLsizeiptr size, GLintptr offset = 0) { - offset = max(offset, GLintptr(0)); - size = size < 0 ? _size : size; - size = min(size, _size - offset); - if (size <= 0) return; - glInvalidateBufferSubData(type, offset, size); - } - - -// TYPED FUNCTIONS ===================================================================================================== - - template - TypeT* map(GLbitfield access, GLsizeiptr n, GLintptr offset = 0) { - return static_cast(map(access, n * sizeof(TypeT), offset * sizeof(TypeT))); - } - -private: - GLuint _handle; - GLsizeiptr _size; - void* _data; - GLbitfield _mapflags; -}; - -} - -} - -#endif // FENNEC_RENDERERS_OPENGL_LIB_BUFFER_H diff --git a/include/fennec/renderers/opengl/lib/enum.h b/include/fennec/renderers/opengl/lib/enum.h index f7b843a..bb6dfe7 100644 --- a/include/fennec/renderers/opengl/lib/enum.h +++ b/include/fennec/renderers/opengl/lib/enum.h @@ -107,6 +107,20 @@ enum texture_types : GLenum { }; +// Cubemap Faces ======================================================================================================= + +/// +/// \brief OpenGL Cubemap Faces +enum cubemap_faces : GLenum { + CUBEMAP_POSITIVE_X = GL_TEXTURE_CUBE_MAP_POSITIVE_X, //!< Cube Map +X Face + CUBEMAP_NEGATIVE_X = GL_TEXTURE_CUBE_MAP_NEGATIVE_X, //!< Cube Map -X Face + CUBEMAP_POSITIVE_Y = GL_TEXTURE_CUBE_MAP_POSITIVE_Y, //!< Cube Map +Y Face + CUBEMAP_NEGATIVE_Y = GL_TEXTURE_CUBE_MAP_NEGATIVE_Y, //!< Cube Map -Y Face + CUBEMAP_POSITIVE_Z = GL_TEXTURE_CUBE_MAP_POSITIVE_Z, //!< Cube Map +Z Face + CUBEMAP_NEGATIVE_Z = GL_TEXTURE_CUBE_MAP_NEGATIVE_Z, //!< Cube Map -Z Face +}; + + // Built-In Types ====================================================================================================== /// @@ -259,6 +273,9 @@ enum types : GLenum { UINT_ATOMIC_COUNTER = GL_UNSIGNED_INT_ATOMIC_COUNTER, //!< Atomic Counter }; + +// Pixel Components ==================================================================================================== + /// /// \brief OpenGL Pixel Components enum pixel_components : GLenum { @@ -287,10 +304,13 @@ enum pixel_components : GLenum { DEPTH_STENCIL = GL_DEPTH_STENCIL, //!< Combined Depth-Stencil }; + +// Pixel Formats ======================================================================================================= + /// -/// \brief OpenGL Color Formats -/// \note UNORM formats are integers interpreted in the normalized range \f$[0.0, 1.0]\f$ -/// \note SNORM formats are integers interpreted in the normalized range \f$[-1.0, 1.0]\f$ +/// \brief OpenGL Pixel Formats +/// \note UNORM formats are integers interpreted in the normalized range \math{[0.0, 1.0]} +/// \note SNORM formats are integers interpreted in the normalized range \math{[-1.0, 1.0]} enum pixel_formats : GLint { R8_UNORM = GL_R8, //!< 8-Bit Unsigned Normalized Single Component Color R8_SNORM = GL_R8_SNORM, //!< 8-Bit Signed Normalized Single Component Color @@ -378,6 +398,20 @@ enum pixel_formats : GLint { SRGBA_DXT5 = GL_COMPRESSED_SRGB_ALPHA_S3TC_DXT5_EXT, //!< Compressed sRGBA DXT5 Color }; + +// Framebuffer Attachments ============================================================================================= + + +/// +/// \brief OpenGL Framebuffer Attachments +enum framebuffer_attachments { + NO_ATTACHMENT = GL_NONE, //!< No Attachment + DEPTH_ATTACHMENT = GL_DEPTH_ATTACHMENT, //!< Depth Attachment + STENCIL_ATTACHMENT = GL_STENCIL_ATTACHMENT, //!< Stencil Attachment + DEPTH_STENCIL_ATTACHMENT = GL_DEPTH_STENCIL_ATTACHMENT, //!< Depth Stencil Attachment + COLOR_ATTACHMENT = GL_COLOR_ATTACHMENT0, //!< Color Attachment +}; + } } diff --git a/include/fennec/renderers/opengl/lib/texture.h b/include/fennec/renderers/opengl/lib/texture.h deleted file mode 100644 index eb6176d..0000000 --- a/include/fennec/renderers/opengl/lib/texture.h +++ /dev/null @@ -1,331 +0,0 @@ -// ===================================================================================================================== -// fennec, a free and open source game engine -// Copyright © 2025 - 2026 Medusa Slockbower -// -// This program is free software: you can redistribute it and/or modify -// it under the terms of the GNU General Public License as published by -// the Free Software Foundation, either version 3 of the License, or -// (at your option) any later version. -// -// This program is distributed in the hope that it will be useful, -// but WITHOUT ANY WARRANTY; without even the implied warranty of -// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -// GNU General Public License for more details. -// -// You should have received a copy of the GNU General Public License -// along with this program. If not, see . -// ===================================================================================================================== - -/// -/// \file fennec/renderers/opengl/lib/texture.h -/// \brief -/// -/// -/// \details -/// \author Medusa Slockbower -/// -/// \copyright Copyright © 2025 - 2026 Medusa Slockbower ([GPLv3](https://www.gnu.org/licenses/gpl-3.0.en.html)) -/// -/// - -#ifndef FENNEC_RENDERERS_OPENGL_LIB_TEXTURE_H -#define FENNEC_RENDERERS_OPENGL_LIB_TEXTURE_H - -/* Because our implementation targets minimum OpenGL ES 3.2, - * we are guaranteed to have the following relevant extensions (Starting from OpenGL ES 3.0): - * - * OES_texture_compression_astc - * EXT_texture_border_clamp - * OES_EGL_image_external_essl3 - * ARB_shader_image_load_store - * ARB_stencil_texturing - * ARG_shader_image_size - * ARB_texture_multisample - * ARB_texture_storage_multisample - * ARB_sample_locations - * OES_texture_view - * NV_image_formats - * EXT_render_snorm - * EXT_render_norm16 - * EXT_color_buffer_float - * OES_copy_image - * OES_shader_image_atomic - * OES_texture_border_clamp - * OES_texture_buffer - * OES_texture_cube_map_array - * OES_texture_stencil8 - * OES_texture_storage_multisample_2d_array - */ - - -#include -#include -#include - -namespace fennec -{ - -namespace gl -{ - -template using texture1d = texture; -template using texture1d_array = texture; -template using texture2d = texture; -template using texture2d_array = texture; -template using texture_rect = texture; -template using texture2d_ms = texture; -template using texture2d_ms_array = texture; -template using cubemap = texture; -template using cubemap_array = texture; -template using texture3d = texture; -template using buffer_texture = texture; - -/// -/// \brief Wrapper for OpenGL Texture Objects -/// \tparam TypeV The type of the texture -/// \tparam FormatV The internal pixel format -/// \tparam ImmutableV Mutability -/// -/// \details Immutable textures require EXT_texture_storage or ARB_texture_storage -/// Immutable multisample textures require ARB_texture_storage_multisample of OES_texture_storage_multisample_2d_array -template -class texture { - -// Constants =========================================================================================================== - -public: - static constexpr GLenum type = TypeV; - static constexpr GLint format = FormatV; - static constexpr GLboolean immutable = ImmutableV; - static constexpr GLboolean is_rect = type == TEXTURE_RECTANGLE; - static constexpr GLboolean is_buffered = type == BUFFER_TEXTURE; - static constexpr GLboolean sampled = type == TEXTURE_2D_MS or type == TEXTURE_2D_MS_ARRAY; - static constexpr GLboolean cubemap = type == CUBEMAP or type == CUBEMAP_ARRAY; - static constexpr GLboolean is_1d = type == TEXTURE_1D or type == TEXTURE_1D_ARRAY; - static constexpr GLboolean is_2d = sampled or is_rect or type == TEXTURE_2D or type == TEXTURE_2D_ARRAY or cubemap; - static constexpr GLboolean is_array = type == TEXTURE_1D_ARRAY or type == TEXTURE_2D_ARRAY or type == TEXTURE_2D_MS_ARRAY or type == CUBEMAP_ARRAY; - static constexpr GLboolean is_3d = type == TEXTURE_3D; - static constexpr GLboolean has_mipmaps = not(sampled or is_rect or is_buffered); - - static constexpr GLboolean use_1d = is_1d and not is_array; - static constexpr GLboolean use_2d = ((is_2d and not is_array) or (is_1d and is_array)) and not sampled; - static constexpr GLboolean use_3d = (is_3d or (is_2d and is_array)) and not (sampled or cubemap); - - static constexpr GLint cubemap_faces = 6; - static constexpr GLenum base_cubemap_face = GL_TEXTURE_CUBE_MAP_POSITIVE_X; - - static constexpr GLboolean compressed = type == RGB_DXT1 or type == RGBA_DXT1 or type == RGBA_DXT3 or type == RGBA_DXT5 - or type == SRGB_DXT1 or type == SRGBA_DXT1 or type == SRGBA_DXT3 or type == SRGBA_DXT5; - - -// Constructors ======================================================================================================== - - /// - /// \brief 1D Texture Constructor - /// \param width The width of the texture - /// \param mips The number of mipmap levels - /// \param data A pointer to a buffer containing pixel values, used as an offset if a PIXEL_UNPACK_BUFFER is bound. - /// \param component The type of each component - /// \param layout The layout of components in each pixel - /// \param size The size of the image data in bytes, for compressed pixel formats - texture(GLsizei width, GLint mips, - void* data = nullptr, GLenum component = BYTE, GLenum layout = R, GLsizei size = 0) requires use_1d - : _handle(NULL) - , _width(width), _height(1), _depth(1) - , _samples(1), _mips(mips) { - glGenTextures(1, &_handle); - start(); - if constexpr(immutable) { - glTexStorage1D(type, _mips, format, _width); - glTexSubImage1D(type, 0, 0, _width, layout, component, data); - } else if constexpr(compressed) { - glCompressedTexImage1D(type, 0, format, _width, 0, size, data); - } else { - glTexImage1D(type, 0, format, _width, 0, layout, component, data); - } - genmips(); - } - - /// - /// \brief 2D Texture Constructor - /// \param width The width of the texture - /// \param height The height of the texture, or number of layers for arrays - /// \param mips The number of mipmap levels - /// \param data A pointer to a buffer containing pixel values, used as an offset if a PIXEL_UNPACK_BUFFER is bound. - /// \param component The type of each component - /// \param layout The layout of components in each pixel - /// \param size The size of the image data in bytes, for compressed pixel formats - texture(GLsizei width, GLsizei height, GLint mips, - void* data = nullptr, GLenum component = BYTE, GLenum layout = R, GLsizei size = 0) requires use_2d and not cubemap - : _handle(NULL) - , _width(width), _height(height), _depth(1) - , _samples(1), _mips(mips) { - glGenTextures(1, &_handle); - start(); - if constexpr(immutable) { - glTexStorage2D(type, _mips, format, _width, _height); - glTexSubImage2D(type, 0, 0, 0, _width, _height, layout, component, data); - } else if constexpr(compressed) { - glCompressedTexImage2D(type, 0, format, _width, _height, 0, size, data); - } else { - glTexImage2D(type, 0, format, _width, _height, 0, layout, component, data); - } - } - - /// - /// \brief 2D Texture Constructor - /// \param width The width of the texture - /// \param height The height of the texture - /// \param depth The depth of the texture, or number of layers for arrays - /// \param mips The number of mipmap levels - /// \param data A pointer to a buffer containing pixel values, used as an offset if a PIXEL_UNPACK_BUFFER is bound. - /// \param component The type of each component - /// \param layout The layout of components in each pixel - /// \param size The size of the image data in bytes, for compressed pixel formats - texture(GLsizei width, GLsizei height, GLsizei depth, GLsizei mips, - void* data = nullptr, GLenum component = BYTE, GLenum layout = R, GLsizei size = 0) requires use_3d and not cubemap - : _handle(NULL) - , _width(width), _height(height), _depth(depth) - , _samples(1), _mips(mips) { - glGenTextures(1, &_handle); - start(); - if constexpr(immutable) { - glTexStorage3D(type, _mips, format, _width, _height, _depth); - glTexSubImage3D(type, 0, 0, 0, 0, _width, _height, _depth, layout, component, data); - } else if constexpr(compressed) { - glCompressedTexImage3D(type, 0, format, _width, _height, _depth, 0, size, data); - } else { - glTexImage3D(type, 0, format, _width, _height, _depth, 0, layout, component, data); - } - } - - /// - /// \brief 2D Multisample Texture Constructor - /// \param width The width of the texture - /// \param height The height of the texture - /// \param samples The number of samples per pixel - /// \param fixed When true, a fixed set of sample locations is used - texture(GLsizei width, GLsizei height, GLsizei samples, GLboolean fixed = true) requires sampled and not is_array - : _handle(NULL) - , _width(width), _height(height), _depth(1) - , _samples(samples), _mips(0) { - glGenTextures(1, &_handle); - start(); - if constexpr(immutable) { - glTexStorage2DMultisample(type, _samples, format, _width, _height, fixed); - } else { - glTexImage2DMultisample(type, _samples, format, _width, _height, fixed); - } - } - - /// - /// \brief 2D Multisample Array Texture Constructor - /// \param width The width of the texture - /// \param height The height of the texture - /// \param depth The number of layers in the array - /// \param samples The number of samples per pixel - /// \param fixed When true, a fixed set of sample locations is used - texture(GLsizei width, GLsizei height, GLsizei depth, GLsizei samples, GLboolean fixed = true) requires sampled and is_array - : _handle(NULL) - , _width(width), _height(height), _depth(depth) - , _samples(samples), _mips(0) { - glGenTextures(1, &_handle); - start(); - if constexpr(immutable) { - glTexStorage3DMultisample(type, _samples, format, _width, _height, _depth, fixed); - } else { - glTexImage3DMultisample(type, _samples, format, _width, _height, _depth, fixed); - } - } - - /// - /// \brief Cubemap Constructor - /// \param size The size of each face texture - /// \param mips The number of mipmap layers - /// \param faces An array of pointers to textures containing pixel data for each face - /// \param component The component type of the data - /// \param layout The layout of the components in the pixel - /// \param bytes The size of the image data in bytes, for compressed pixel formats - texture(GLsizei size, GLsizei mips, - const void* faces[6], GLenum component = BYTE, GLenum layout = R, GLsizei bytes = 0) requires is_2d and cubemap - : _handle(NULL) - , _width(size), _height(size), _depth(1) - , _samples(1), _mips(mips) { - glGenTextures(1, &_handle); - start(); - if constexpr(immutable) { - glTexStorage2D(type, _mips, format, _width, _height); - for (int i = 0; i < cubemap_faces; ++i) { - glTexSubImage2D(base_cubemap_face + i, 0, 0, 0, _width, _height, layout, component, faces[i]); - } - } else if constexpr(compressed) { - for (int i = 0; i < cubemap_faces; ++i) { - glCompressedTexImage2D(base_cubemap_face + i, 0, format, _width, _height, 0, bytes, faces[i]); - } - } else { - for (int i = 0; i < cubemap_faces; ++i) { - glTexImage2D(base_cubemap_face + i, 0, format, _width, _height, 0, layout, component, faces[i]); - } - } - } - - /// - /// \brief Cubemap Array Constructor - /// \param size The size of each face texture - /// \param depth The number of layers in the array - /// \param mips The number of mipmap layers - /// \param data A pointer to a buffer containing image data - /// \param component The component type of the data - /// \param layout The layout of the components in the pixel - /// \param bytes The size of the image data in bytes, for compressed pixel formats - /// - /// \details Requires OES_texture_cube_map_array - texture(GLsizei size, GLsizei depth, GLsizei mips, - const void* data, GLenum component = BYTE, GLenum layout = R, GLsizei bytes = 0) requires is_2d and cubemap - : _handle(NULL) - , _width(size), _height(size), _depth(depth) - , _samples(1), _mips(mips) { - glGenTextures(1, &_handle); - start(); - if constexpr(immutable) { - glTexStorage3D(type, _mips, format, _width, _height, _depth * 6); - glTexSubImage3D(type, 0, 0, 0, 0, _width, _height, _depth * 6, layout, component, data); - } else if constexpr(compressed) { - for (int i = 0; i < cubemap_faces; ++i) { - glCompressedTexImage3D(type, 0, format, _width, _height, _depth * 6, 0, bytes, data); - } - } else { - glTexImage3D(type, 0, format, _width, _height, _depth * 6, 0, layout, component, data); - } - } - - -// Basic Functions ===================================================================================================== - - void use() { - glBindTexture(type, _handle); - } - - void bind(GLint i) { - glActiveTexture(GL_TEXTURE0 + i); - use(); - } - - void genmips() { - glGenerateMipmap(type); - } - -private: - GLuint _handle; - GLsizei _width; - GLsizei _height; - GLsizei _depth; - GLsizei _samples; - GLint _mips; -}; - -} - -} - -#endif // FENNEC_RENDERERS_OPENGL_LIB_TEXTURE_H diff --git a/include/fennec/renderers/vulkan/lib/app_info.h b/include/fennec/renderers/vulkan/lib/app_info.h index 7b15631..c41cc98 100644 --- a/include/fennec/renderers/vulkan/lib/app_info.h +++ b/include/fennec/renderers/vulkan/lib/app_info.h @@ -32,7 +32,7 @@ #ifndef FENNEC_RENDERERS_VULKAN_LIB_APP_INFO_H #define FENNEC_RENDERERS_VULKAN_LIB_APP_INFO_H -#include +#include #include #include @@ -44,6 +44,12 @@ namespace fennec::vk /// \brief Wrapper class for VkApplicationInfo struct app_info : private VkApplicationInfo { +// Definitions ========================================================================================================= +private: + + + + // Constructors & Destructor =========================================================================================== public: @@ -52,30 +58,36 @@ public: /// /// \brief Create a Vulkan application information structure - /// \param app_name the name of the application, this cstring must exist for the lifetime of this object - /// until a structure of type fennec::vk::instance is constructed + /// \param app_name the name of the application. /// \param app_version the internal version of the application - /// \param engine_name the name of the engine, this cstring must exist for the lifetime of this object - /// until a structure of type fennec::vk::instance is constructed + /// \param engine_name the name of the engine. /// \param engine_version the internal version of the engine - /// \param api_version the Vulkan API version to use, version::patch and version::str are ignored /// \param ext a pointer to an extension structure, the object next points to must exist for the lifetime of this /// object until a structure of type fennec::vk::instance is constructed /// TODO: DEFINE EXTENSION STRUCTURE WRAPPERS app_info( const cstring& app_name = {}, const version& app_version = {}, - const cstring& engine_name = {}, const version& engine_version = {}, - const version& api_version = {}, - void* ext = nullptr + const cstring& engine_name = {}, const version& engine_version = {} ) noexcept : VkApplicationInfo { .sType = VK_STRUCTURE_TYPE_APPLICATION_INFO, - .pNext = ext, - .pApplicationName = app_name, + .pNext = nullptr, + .pApplicationName = nullptr, .applicationVersion = VK_MAKE_VERSION(app_version.major, app_version.minor, app_version.patch), - .pEngineName = engine_name, + .pEngineName = nullptr, .engineVersion = VK_MAKE_VERSION(engine_version.major, engine_version.minor, engine_version.patch), - .apiVersion = VK_MAKE_API_VERSION(0, api_version.major, api_version.minor, 0), - } { + .apiVersion = VK_MAKE_API_VERSION(0, 1, 0, 0), // Default to 1.0 + }, _app_name(app_name) + , _engine_name(engine_name) { + + pApplicationName = _app_name.data(); + pEngineName = _engine_name.data(); + + // Attempt to acquire version supported by the driver + if (vkEnumerateInstanceVersion) { + uint32_t api_version; + vkEnumerateInstanceVersion(&api_version); + apiVersion = VK_MAKE_API_VERSION(0, VK_API_VERSION_MAJOR(api_version), VK_API_VERSION_MINOR(api_version), 0); + } } /// @@ -102,13 +114,13 @@ public: /// /// \brief Copy Assignment /// \param info The app_info object to move - /// \returns A reference to self + /// \returns A reference to \emph{this} app_info& operator=(const app_info& info) noexcept = default; /// /// \brief Move Assignment /// \param info The app_info object to move - /// \returns A reference to self + /// \returns A reference to \emph{this} app_info& operator=(app_info&& info) noexcept = default; /// @} @@ -121,14 +133,14 @@ public: /// @{ /// - /// \returns \f$this\f$ as if it were a pointer to the underlying type, \f$VkApplicationInfo\f$. + /// \returns \emph{this} as if it were a pointer to the underlying type, \emph{VkApplicationInfo}. operator VkApplicationInfo*() noexcept { return this; } /// /// \brief Implicit Pointer Conversion - /// \returns \f$this\f$ as if it were a pointer to the underlying type, \f$VkApplicationInfo\f$. + /// \returns \emph{this} as if it were a pointer to the underlying type, \emph{VkApplicationInfo}. operator const VkApplicationInfo*() const noexcept { return this; } @@ -168,18 +180,22 @@ public: /// /// \brief Set the engine version /// \param ver A version struct containing the new version - void set_engine_version(const version& ver) { - engineVersion = VK_MAKE_VERSION(ver.major, ver.minor, ver.patch); + void set_app_version(const version& ver) { + applicationVersion = VK_MAKE_VERSION(ver.major, ver.minor, ver.patch); } /// /// \returns A cstring containing the engine name - cstring get_engine_name() const { return cstring(pEngineName, strlen(pEngineName)); } + cstring get_engine_name() const { + return { pEngineName, strlen(pEngineName) }; + } /// /// \brief Set the engine name /// \param str A cstring containing the new name - void set_engine_name(const cstring& str) { pEngineName = str; } + void set_engine_name(const cstring& str) { + pEngineName = str; + } /// /// \returns A version struct containing the engine version @@ -203,7 +219,9 @@ public: version get_api_version() const { return version { .major = VK_API_VERSION_MAJOR(apiVersion), - .minor = VK_API_VERSION_MINOR(apiVersion) + .minor = VK_API_VERSION_MINOR(apiVersion), + .patch = VK_API_VERSION_PATCH(apiVersion), + .meta = VK_API_VERSION_VARIANT(apiVersion), }; } @@ -222,7 +240,7 @@ public: } /// - /// \brief Clear the extension structure with \f$nullptr\f$ + /// \brief Clear the extension structure with \emph{nullptr} void set_extension(nullptr_t) { pNext = nullptr; } @@ -232,6 +250,8 @@ public: // Private Member Variables ============================================================================================ private: + string _app_name; + string _engine_name; }; } diff --git a/include/fennec/renderers/vulkan/lib/debug.h b/include/fennec/renderers/vulkan/lib/debug.h new file mode 100644 index 0000000..31300ec --- /dev/null +++ b/include/fennec/renderers/vulkan/lib/debug.h @@ -0,0 +1,145 @@ +// ===================================================================================================================== +// fennec, a free and open source game engine +// Copyright © 2025 Medusa Slockbower +// +// This program is free software: you can redistribute it and/or modify +// it under the terms of the GNU General Public License as published by +// the Free Software Foundation, either version 3 of the License, or +// (at your option) any later version. +// +// This program is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. +// +// You should have received a copy of the GNU General Public License +// along with this program. If not, see . +// ===================================================================================================================== + +/// +/// \file debug.h +/// \brief +/// +/// +/// \details +/// \author Medusa Slockbower +/// +/// \copyright Copyright © 2025 - 2026 Medusa Slockbower ([GPLv3](https://www.gnu.org/licenses/gpl-3.0.en.html)) +/// +/// + + +#ifndef FENNEC_RENDERERS_VULKAN_LIB_DEBUG_H +#define FENNEC_RENDERERS_VULKAN_LIB_DEBUG_H + +#include +#include +#include +#include +#include +#include + +namespace fennec::vk +{ + +/// +/// \brief Vulkan Debugger Interface +class debugger { + +// Definitions ========================================================================================================= +public: + + /// + /// \brief Info for attaching a debugger to an instance. + struct info + : private VkDebugUtilsMessengerCreateInfoEXT + { + explicit info(const debugger& dbg) + : VkDebugUtilsMessengerCreateInfoEXT { + .sType = VK_STRUCTURE_TYPE_DEBUG_UTILS_MESSENGER_CREATE_INFO_EXT, + .pNext = nullptr, + .flags = 0, + .messageSeverity = debug_message_severity_all, + .messageType = debug_message_type_all, + .pfnUserCallback = _debug_message, + .pUserData = const_cast(&dbg), + } { + } + + operator const VkDebugUtilsMessengerCreateInfoEXT*() const { + return this; + } + }; + + +// Properties ========================================================================================================== +public: + + /// + /// \brief Instance Creation Info + /// \returns An info object for attaching this debugger to an instance. + info get_info() const { + return info(*this); + } + + +// Debug Callbacks ===================================================================================================== +public: + + /// + /// \brief + /// \param severity The message severity + /// \param type The message type + /// \param id The message id + /// \param message The message string + /// \param queue The labels in the queue + /// \param commands The labels in the command buffer + /// \param objects The related objects + virtual void message(uint32_t severity, + uint32_t type, + const cstring& id, + const cstring& message, + const dynarray& queue, + const dynarray& commands, + const dynarray& objects) = 0; + + +// Private Helper Functions ============================================================================================ +private: + + static VkBool32 _debug_message( + VkDebugUtilsMessageSeverityFlagBitsEXT messageSeverity, + VkDebugUtilsMessageTypeFlagsEXT messageType, + const VkDebugUtilsMessengerCallbackDataEXT* pCallbackData, + void* pUserData + ) { + const cstring id = cstring(pCallbackData->pMessageIdName, strlen(pCallbackData->pMessageIdName)); + const cstring message = cstring(pCallbackData->pMessage, strlen(pCallbackData->pMessage)); + + dynarray queue; + dynarray commands; + dynarray objects; + + debugger* dbg = static_cast(pUserData); + + for (const auto& label : range(pCallbackData->pQueueLabels, pCallbackData->pQueueLabels + pCallbackData->queueLabelCount)) { + queue.emplace_back(label.pLabelName, strlen(label.pLabelName)); + } + + for (const auto& label : range(pCallbackData->pCmdBufLabels, pCallbackData->pCmdBufLabels + pCallbackData->cmdBufLabelCount)) { + commands.emplace_back(label.pLabelName, strlen(label.pLabelName)); + } + + for (const auto& obj : range(pCallbackData->pObjects, pCallbackData->pObjects + pCallbackData->objectCount)) { + objects.push_back(format("{:#016x} ({})", obj.objectHandle, object_string(obj.objectType))); + } + + dbg->message(messageSeverity, messageType, id, message, queue, commands, objects); + + return VK_FALSE; + } +}; + +} + +#endif // FENNEC_RENDERERS_VULKAN_LIB_DEBUG_H \ No newline at end of file diff --git a/include/fennec/renderers/vulkan/lib/enum.h b/include/fennec/renderers/vulkan/lib/enum.h new file mode 100644 index 0000000..b07ba98 --- /dev/null +++ b/include/fennec/renderers/vulkan/lib/enum.h @@ -0,0 +1,359 @@ +// ===================================================================================================================== +// fennec, a free and open source game engine +// Copyright © 2025 Medusa Slockbower +// +// This program is free software: you can redistribute it and/or modify +// it under the terms of the GNU General Public License as published by +// the Free Software Foundation, either version 3 of the License, or +// (at your option) any later version. +// +// This program is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. +// +// You should have received a copy of the GNU General Public License +// along with this program. If not, see . +// ===================================================================================================================== + +/// +/// \file enum.h +/// \brief +/// +/// +/// \details +/// \author Medusa Slockbower +/// +/// \copyright Copyright © 2025 - 2026 Medusa Slockbower ([GPLv3](https://www.gnu.org/licenses/gpl-3.0.en.html)) +/// +/// + + +#ifndef FENNEC_RENDERERS_VULKAN_LIB_ENUM_H +#define FENNEC_RENDERERS_VULKAN_LIB_ENUM_H + +#include + +namespace fennec::vk +{ + +// Objects ============================================================================================================= + +/// +/// \brief An enum representing the Vulkan object types +enum object_ : uint32_t { + object_unknown = VK_OBJECT_TYPE_UNKNOWN, //!< Unknown type + object_instance = VK_OBJECT_TYPE_INSTANCE, //!< Vulkan Instance + object_physical_device = VK_OBJECT_TYPE_PHYSICAL_DEVICE, //!< Physical Device + object_logical_device = VK_OBJECT_TYPE_DEVICE, //!< Logical Device + object_queue = VK_OBJECT_TYPE_QUEUE, //!< Queue + object_semaphore = VK_OBJECT_TYPE_SEMAPHORE, //!< Semaphore + object_command_buffer = VK_OBJECT_TYPE_COMMAND_BUFFER, //!< Command Buffer + object_fence = VK_OBJECT_TYPE_FENCE, //!< Fence + object_device_memory = VK_OBJECT_TYPE_DEVICE_MEMORY, //!< Device Memory + object_buffer = VK_OBJECT_TYPE_BUFFER, //!< Buffer + object_image = VK_OBJECT_TYPE_IMAGE, //!< Image + object_event = VK_OBJECT_TYPE_EVENT, //!< Event + object_query_pool = VK_OBJECT_TYPE_QUERY_POOL, //!< Query Pool + object_buffer_view = VK_OBJECT_TYPE_BUFFER_VIEW, //!< Buffer View + object_image_view = VK_OBJECT_TYPE_IMAGE_VIEW, //!< Image View + object_shader_module = VK_OBJECT_TYPE_SHADER_MODULE, //!< Shader Module + object_pipeline_cache = VK_OBJECT_TYPE_PIPELINE_CACHE, //!< Pipeline Cache + object_pipeline_layout = VK_OBJECT_TYPE_PIPELINE_LAYOUT, //!< Pipeline Layout + object_render_pass = VK_OBJECT_TYPE_RENDER_PASS, //!< Render Pass + object_pipeline = VK_OBJECT_TYPE_PIPELINE, //!< Pipeline + object_descriptor_set_layout = VK_OBJECT_TYPE_DESCRIPTOR_SET_LAYOUT, //!< Descriptor Set + object_sampler = VK_OBJECT_TYPE_SAMPLER, //!< Sampler + object_descriptor_pool = VK_OBJECT_TYPE_DESCRIPTOR_POOL, //!< Descriptor Pool + object_descriptor_set = VK_OBJECT_TYPE_DESCRIPTOR_SET, //!< Descriptor Set + object_framebuffer = VK_OBJECT_TYPE_FRAMEBUFFER, //!< Framebuffer + object_command_pool = VK_OBJECT_TYPE_COMMAND_POOL, //!< Command Pool + object_sampler_ycbcr_conversion = VK_OBJECT_TYPE_SAMPLER_YCBCR_CONVERSION, //!< YCBCR Conversion Sampler + object_descriptor_update_template = VK_OBJECT_TYPE_DESCRIPTOR_UPDATE_TEMPLATE, //!< Descriptor Update Template + object_private_data_slot = VK_OBJECT_TYPE_PRIVATE_DATA_SLOT, //!< Private Data Slot + object_debug_report_callback_ext = VK_OBJECT_TYPE_DEBUG_REPORT_CALLBACK_EXT, //!< Debug Report Callback + object_debug_utils_messenger_ext = VK_OBJECT_TYPE_DEBUG_UTILS_MESSENGER_EXT, //!< Debug Utility Messenger + object_validation_cache_ext = VK_OBJECT_TYPE_VALIDATION_CACHE_EXT, //!< Validation Cache + object_micromap_ext = VK_OBJECT_TYPE_MICROMAP_EXT, //!< Micro-Map + object_shader_ext = VK_OBJECT_TYPE_SHADER_EXT, //!< Shader + object_indirect_commands_layout_ext = VK_OBJECT_TYPE_INDIRECT_COMMANDS_LAYOUT_EXT, //!< Indirect Commands Layout + object_indirect_execution_set_ext = VK_OBJECT_TYPE_INDIRECT_EXECUTION_SET_EXT, //!< Indirect Execution Set + + object_surface = VK_OBJECT_TYPE_SURFACE_KHR, //!< Surface + object_swapchain = VK_OBJECT_TYPE_SWAPCHAIN_KHR, //!< Swap-chain + object_display = VK_OBJECT_TYPE_DISPLAY_KHR, //!< Display + object_display_mode = VK_OBJECT_TYPE_DISPLAY_MODE_KHR, //!< Display Mode + object_video_session = VK_OBJECT_TYPE_VIDEO_SESSION_KHR, //!< Video Session + object_video_session_parameters = VK_OBJECT_TYPE_VIDEO_SESSION_PARAMETERS_KHR, //!< Video Session Parameters + object_acceleration_structure = VK_OBJECT_TYPE_ACCELERATION_STRUCTURE_KHR, //!< Acceleration Structure + object_deferred_operation = VK_OBJECT_TYPE_DEFERRED_OPERATION_KHR, //!< Deferred Operation + object_pipeline_binary = VK_OBJECT_TYPE_PIPELINE_BINARY_KHR, //!< Pipeline Binary + + object_acceleration_structure_NV = VK_OBJECT_TYPE_ACCELERATION_STRUCTURE_NV, //!< NV Acceleration Structure + object_indirect_commands_layout_NV = VK_OBJECT_TYPE_INDIRECT_COMMANDS_LAYOUT_NV, //!< NV Indirect Commands Layout + object_optical_flow_session_NV = VK_OBJECT_TYPE_OPTICAL_FLOW_SESSION_NV, //!< NV Optical Flow Session + object_external_compute_queue_NV = VK_OBJECT_TYPE_EXTERNAL_COMPUTE_QUEUE_NV, //!< NV External Compute Queue + + object_cu_module_NVX = VK_OBJECT_TYPE_CU_MODULE_NVX, //!< NVX CU Module + object_cu_function_NVX = VK_OBJECT_TYPE_CU_FUNCTION_NVX, //!< NVX CU Function + + object_performance_configuration_INTEL = VK_OBJECT_TYPE_PERFORMANCE_CONFIGURATION_INTEL, //!< Intel Performance Configuration + + object_buffer_collection_FUCHSIA = VK_OBJECT_TYPE_BUFFER_COLLECTION_FUCHSIA, //!< Fuchsia Buffer Collection + + object_tensor_ARM = VK_OBJECT_TYPE_TENSOR_ARM, //!< ARM Tensor + object_tensor_view_ARM = VK_OBJECT_TYPE_TENSOR_VIEW_ARM, //!< ARM Tensor View + object_data_graph_pipeline_session_ARM = VK_OBJECT_TYPE_DATA_GRAPH_PIPELINE_SESSION_ARM, //!< ARM Data Graph Pipeline Session + + // Beta Extensions +#ifdef VK_ENABLE_BETA_EXTENSIONS + object_cuda_module_NV = VK_OBJECT_TYPE_CUDA_MODULE_NV, //!< NV Cuda Module + object_cuda_function_NV = VK_OBJECT_TYPE_CUDA_FUNCTION_NV, //!< NV Cuda Function +#endif +}; + +inline cstring object_string(uint32_t flag) { + switch (flag) { + default: + case object_unknown: return "Unknown"; + case object_instance: return "Instance"; + case object_physical_device: return "Physical Device"; + case object_logical_device: return "Logical Device"; + case object_queue: return "Queue"; + case object_semaphore: return "Semaphore"; + case object_command_buffer: return "Command Buffer"; + case object_fence: return "Fence"; + case object_device_memory: return "Device Memory"; + case object_buffer: return "Buffer"; + case object_image: return "Image"; + case object_event: return "Event"; + case object_query_pool: return "Query Pool"; + case object_buffer_view: return "Buffer View"; + case object_image_view: return "Image View"; + case object_shader_module: return "Shader Module"; + case object_pipeline_cache: return "Pipeline Cache"; + case object_pipeline_layout: return "Pipeline Layout"; + case object_render_pass: return "Render Pass"; + case object_pipeline: return "Pipeline"; + case object_descriptor_set_layout: return "Descriptor Set Layout"; + case object_sampler: return "Sampler"; + case object_descriptor_pool: return "Descriptor Pool"; + case object_descriptor_set: return "Descriptor Set"; + case object_framebuffer: return "Framebuffer"; + case object_command_pool: return "Command Pool"; + case object_sampler_ycbcr_conversion: return "YCBCR Conversion Sampler"; + case object_descriptor_update_template: return "Descriptor Update Template"; + case object_private_data_slot: return "Private Data Slot"; + case object_debug_report_callback_ext: return "Report Callback"; + case object_debug_utils_messenger_ext: return "Debug Messenger"; + case object_validation_cache_ext: return "Validation Cache"; + case object_micromap_ext: return "Micro-Map"; + case object_shader_ext: return "Shader"; + case object_indirect_commands_layout_ext: return "Indirect Commands Layout"; + case object_indirect_execution_set_ext: return "Indirect Execution Set"; + + case object_surface: return "Surface"; + case object_swapchain: return "Swap-Chain"; + case object_display: return "Display"; + case object_display_mode: return "Display Mode"; + case object_video_session: return "Video Session"; + case object_video_session_parameters: return "Video Session Parameters"; + case object_acceleration_structure: return "Acceleration Structure"; + case object_deferred_operation: return "Deferred Operation"; + case object_pipeline_binary: return "Pipeline Binary"; + + case object_acceleration_structure_NV: return "NV Acceleration Structure"; + case object_indirect_commands_layout_NV: return "NV Indirect Commands Layout"; + case object_optical_flow_session_NV: return "NV Optical Flow Session"; + case object_external_compute_queue_NV: return "NV External Compute Queue"; + + case object_cu_module_NVX: return "NVX CU Module"; + case object_cu_function_NVX: return "NVX CU Function"; + + case object_performance_configuration_INTEL: return "Intel Performance Configuration"; + + case object_buffer_collection_FUCHSIA: return "Fuchsia Buffer Collection"; + + case object_tensor_ARM: return "ARM Tensor"; + case object_tensor_view_ARM: return "ARM Tensor View"; + case object_data_graph_pipeline_session_ARM: return "ARM Data Graph Pipeline Session"; + + // Beta Extensions +#ifdef VK_ENABLE_BETA_EXTENSIONS + case object_cuda_module_NV: return "NV CUDA Module", + case object_cuda_function_NV: return "NV CUDA Function", +#endif + } +} + +// Physical Devices ==================================================================================================== + +/// +/// \brief An enum representing the Vulkan physical device types +enum device_ : uint32_t { + device_other = VK_PHYSICAL_DEVICE_TYPE_OTHER, //!< Other Type + device_integrated = VK_PHYSICAL_DEVICE_TYPE_INTEGRATED_GPU, //!< Integrated GPU + device_discrete = VK_PHYSICAL_DEVICE_TYPE_DISCRETE_GPU, //!< Discrete / Dedicated GPU + device_virtual = VK_PHYSICAL_DEVICE_TYPE_VIRTUAL_GPU, //!< Virtualized / Software GPU + device_cpu = VK_PHYSICAL_DEVICE_TYPE_CPU, //!< CPU +}; + +/// +/// \brief Get a descriptor string for the provided device type. +/// \param type The device type. +/// \returns A cstring containing a short description. +inline cstring device_string(uint32_t type) { + switch (type) { + default: + case device_other: return "Other"; + case device_integrated: return "iGPU"; + case device_discrete: return "dGPU"; + case device_virtual: return "Virtual"; + case device_cpu: return "CPU"; + } +} + + + +// Instances =========================================================================================================== + +/// +/// \brief An enum representing the Vulkan instance creation flags +enum instance_flag_ : uint32_t { + instance_flag_portability = VK_INSTANCE_CREATE_ENUMERATE_PORTABILITY_BIT_KHR, //!< Portability, allow non-conformant devices + + instance_flag_none = 0, //!< No flags + instance_flag_all = instance_flag_portability, //!< All flags +}; + + +/// +/// \brief Get a descriptor string for the provided device type. +/// \param flag The instance flag. +/// \returns A cstring containing a short description. +inline cstring instance_flag_string(uint32_t flag) { + switch (flag) { + default: + case instance_flag_none: return "None"; + case instance_flag_portability: return "Portability"; + + // TODO: Multi-Flags + + //case instance_flag_all: return cstring("All"); + } +} + + + +// Debugging =========================================================================================================== + +/// +/// \brief An enum representing the Vulkan debug message severity flags +enum debug_message_severity_ : uint32_t { + debug_message_severity_verbose = VK_DEBUG_UTILS_MESSAGE_SEVERITY_VERBOSE_BIT_EXT, //!< Verbose Message + debug_message_severity_info = VK_DEBUG_UTILS_MESSAGE_SEVERITY_INFO_BIT_EXT, //!< Info Message + debug_message_severity_warning = VK_DEBUG_UTILS_MESSAGE_SEVERITY_WARNING_BIT_EXT, //!< Warning Message + debug_message_severity_error = VK_DEBUG_UTILS_MESSAGE_SEVERITY_ERROR_BIT_EXT, //!< Error Message + + debug_message_severity_none = 0, //!< No flags + + debug_message_severity_all = debug_message_severity_verbose + | debug_message_severity_info + | debug_message_severity_warning + | debug_message_severity_error, //!< All flags +}; + +/// +/// \brief Get a descriptor string for the provided message severity. +/// \param flag The severity flag. +/// \returns A cstring containing a short description. +inline cstring message_severity_string(uint32_t flag) { + switch (flag) { + default: + case debug_message_severity_none: return "None"; + case debug_message_severity_verbose: return "Verbose"; + case debug_message_severity_info: return "Info"; + case debug_message_severity_warning: return "Warning"; + case debug_message_severity_error: return "Error"; + + // TODO: Multi-Flags + + case debug_message_severity_all: return "All"; + } +} + + + +/// +/// \brief An enum representing the Vulkan debug message type flags +enum debug_message_type_ : uint32_t { + debug_message_type_general = VK_DEBUG_UTILS_MESSAGE_TYPE_GENERAL_BIT_EXT, //!< General Message + debug_message_type_validation = VK_DEBUG_UTILS_MESSAGE_TYPE_VALIDATION_BIT_EXT, //!< Validation Message + debug_message_type_performance = VK_DEBUG_UTILS_MESSAGE_TYPE_PERFORMANCE_BIT_EXT, //!< Performance Message + + debug_message_type_none = 0, //!< No flags + + debug_message_type_all = debug_message_type_general + | debug_message_type_validation + | debug_message_type_performance, //!< All flags +}; + +/// +/// \brief Get a descriptor string for the provided message type. +/// \param flag The type flag. +/// \returns A cstring containing a short description. +inline cstring message_type_string(uint32_t flag) { + switch (flag) { + default: + case debug_message_type_none: return "None"; + case debug_message_type_general: return "General"; + case debug_message_type_validation: return "Validation"; + case debug_message_type_performance: return "Performance"; + + // TODO: Multi-Flags + + case debug_message_type_all: return "All"; + } +} + + +/// +/// \brief An enum representing the Vulkan debug report flags +enum debug_report_ : uint32_t { + debug_report_information = VK_DEBUG_REPORT_INFORMATION_BIT_EXT, //!< Information Report + debug_report_warning = VK_DEBUG_REPORT_WARNING_BIT_EXT, //!< Warning Report + debug_report_performance = VK_DEBUG_REPORT_PERFORMANCE_WARNING_BIT_EXT, //!< Performance Warning Report + debug_report_error = VK_DEBUG_REPORT_ERROR_BIT_EXT, //!< Error Report + debug_report_debug = VK_DEBUG_REPORT_DEBUG_BIT_EXT, //!< Debug Report + + debug_report_none = 0, //!< No flags + debug_report_all = debug_report_information + | debug_report_warning + | debug_report_performance + | debug_report_error + | debug_report_debug, //!< All flags +}; + +/// +/// \brief Get a descriptor string for the provided report type. +/// \param flag The type flag. +/// \returns A cstring containing a short description. +inline cstring report_string(uint32_t flag) { + switch (flag) { + default: + case debug_report_none: return "None"; + case debug_report_information: return "Information"; + case debug_report_warning: return "Warning"; + case debug_report_performance: return "Performance"; + case debug_report_error: return "Error"; + case debug_report_debug: return "Debug"; + + // TODO: Multi-Flags + + case debug_report_all: return "All"; + } +} + +} + +#endif // FENNEC_RENDERERS_VULKAN_LIB_ENUM_H \ No newline at end of file diff --git a/include/fennec/renderers/vulkan/lib/forward.h b/include/fennec/renderers/vulkan/lib/forward.h new file mode 100644 index 0000000..0a18dad --- /dev/null +++ b/include/fennec/renderers/vulkan/lib/forward.h @@ -0,0 +1,46 @@ +// ===================================================================================================================== +// fennec, a free and open source game engine +// Copyright © 2025 Medusa Slockbower +// +// This program is free software: you can redistribute it and/or modify +// it under the terms of the GNU General Public License as published by +// the Free Software Foundation, either version 3 of the License, or +// (at your option) any later version. +// +// This program is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. +// +// You should have received a copy of the GNU General Public License +// along with this program. If not, see . +// ===================================================================================================================== + +/// +/// \file forward.h +/// \brief +/// +/// +/// \details +/// \author Medusa Slockbower +/// +/// \copyright Copyright © 2025 - 2026 Medusa Slockbower ([GPLv3](https://www.gnu.org/licenses/gpl-3.0.en.html)) +/// +/// + + +#ifndef FENNEC_RENDERERS_VULKAN_LIB_FORWARD_H +#define FENNEC_RENDERERS_VULKAN_LIB_FORWARD_H + +#include + +namespace fennec::vk +{ + +struct app_info; +struct instance; +struct physical_device; + +} + +#endif // FENNEC_RENDERERS_VULKAN_LIB_FORWARD_H \ No newline at end of file diff --git a/include/fennec/renderers/vulkan/lib/instance.h b/include/fennec/renderers/vulkan/lib/instance.h index c4d5848..66ac944 100644 --- a/include/fennec/renderers/vulkan/lib/instance.h +++ b/include/fennec/renderers/vulkan/lib/instance.h @@ -32,10 +32,11 @@ #ifndef FENNEC_RENDERERS_VULKAN_LIB_INSTANCE_H #define FENNEC_RENDERERS_VULKAN_LIB_INSTANCE_H -#include -#include - +#include #include +#include + +#include namespace fennec::vk { @@ -46,6 +47,10 @@ struct instance { // Definitions ========================================================================================================= public: + + /// \name Definitions + /// @{ + using create_flags = VkInstanceCreateFlags; //!< Alias for VkInstanceCreateFlags @@ -56,16 +61,19 @@ public: // Constructors & Destructor --------------------------------------------------------------------------------------- public: + /// \name Constructors & Destructor + /// @{ + /// - /// \brief Constructor, acts as default constructor, takes \f$nullptr\f$ for \f$info\f$ - /// \param flags - /// \param ext + /// \brief Null App Info Constructor + /// \param flags The flags to create the instance with. + /// + /// \note Acts as Default Constructor. create_info( - create_flags flags = {}, nullptr_t = nullptr, - void* ext = nullptr + create_flags flags = {}, nullptr_t = nullptr ) : VkInstanceCreateInfo { .sType = VK_STRUCTURE_TYPE_INSTANCE_CREATE_INFO, - .pNext = ext, + .pNext = nullptr, .flags = flags, .pApplicationInfo = nullptr, .enabledLayerCount = 0, @@ -76,16 +84,17 @@ public: } /// - /// \brief - /// \param flags - /// \param info - /// \param ext + /// \brief App Info Constructor + /// \param flags The flags to create the instance with. + /// \param info A const-qualified reference to an \ref fennec::vk::app_info "app_info" object. + /// + /// \note The object referenced by \emph{info} must have a lifetime that extends until an + /// \ref fennec::vk::instance "instance" is constructed. create_info( - create_flags flags, const app_info& info, - void* ext = nullptr + create_flags flags, const app_info& info ) : VkInstanceCreateInfo { .sType = VK_STRUCTURE_TYPE_INSTANCE_CREATE_INFO, - .pNext = ext, + .pNext = nullptr, .flags = flags, .pApplicationInfo = info, .enabledLayerCount = 0, @@ -95,14 +104,22 @@ public: } { } + /// + /// \brief Layer Constructor + /// \tparam LayersN The number of layers + /// \param flags The flags to create the instance with. + /// \param info A const-qualified reference to an \ref fennec::vk::app_info "app_info" object. + /// \param layers An array of layer names to enable. + /// + /// \note The object referenced by \emph{info} must have a lifetime that extends until an + /// \ref fennec::vk::instance "instance" is constructed. template create_info( create_flags flags, const app_info& info, - const cstring (&layers)[LayersN], nullptr_t, - void* ext + const cstring (&layers)[LayersN], nullptr_t ) : VkInstanceCreateInfo { .sType = VK_STRUCTURE_TYPE_INSTANCE_CREATE_INFO, - .pNext = ext, + .pNext = nullptr, .flags = flags, .pApplicationInfo = info, .enabledLayerCount = LayersN, @@ -111,20 +128,31 @@ public: .ppEnabledExtensionNames = nullptr, } { _layers.reserve(LayersN); - for (const auto& layer : layers) { _layers.push_back(layer); } + for (const auto& layer : layers) { + _layers.push_back(layer); + } ppEnabledLayerNames = _layers.data(); ppEnabledExtensionNames = _extensions.data(); } + + /// + /// \brief Extension Constructor + /// \tparam ExtensionsN The number of extensions + /// \param flags The flags to create the instance with. + /// \param info A const-qualified reference to an \ref fennec::vk::app_info "app_info" object. + /// \param extensions An array of extension names to enable. + /// + /// \note The object referenced by \emph{info} must have a lifetime that extends until an + /// \ref fennec::vk::instance "instance" is constructed. template create_info( create_flags flags, const app_info& info, - nullptr_t, const cstring (&extensions)[ExtensionsN], - void* ext + nullptr_t, const cstring (&extensions)[ExtensionsN] ) : VkInstanceCreateInfo { .sType = VK_STRUCTURE_TYPE_INSTANCE_CREATE_INFO, - .pNext = ext, + .pNext = nullptr, .flags = flags, .pApplicationInfo = info, .enabledLayerCount = 0, @@ -133,20 +161,32 @@ public: .ppEnabledExtensionNames = nullptr, } { _extensions.reserve(ExtensionsN); - for (const auto& extension : extensions) { _extensions.push_back(extension); } + for (const auto& extension : extensions) { + _extensions.push_back(extension); + } ppEnabledLayerNames = _layers.data(); ppEnabledExtensionNames = _extensions.data(); } + /// + /// \brief Layer-Extension Constructor + /// \tparam LayersN The number of layers + /// \tparam ExtensionsN The number of extensions + /// \param flags The flags to create the instance with. + /// \param info A const-qualified reference to an \ref fennec::vk::app_info "app_info" object. + /// \param layers An array of layer names to enable. + /// \param extensions An array of extension names to enable. + /// + /// \note The object referenced by \emph{info} must have a lifetime that extends until an + /// \ref fennec::vk::instance "instance" is constructed. template create_info( create_flags flags, const app_info& info, - const cstring (&layers)[LayersN], const cstring (&extensions)[ExtensionsN], - void* ext + const cstring (&layers)[LayersN], const cstring (&extensions)[ExtensionsN] ) : VkInstanceCreateInfo { .sType = VK_STRUCTURE_TYPE_INSTANCE_CREATE_INFO, - .pNext = ext, + .pNext = nullptr, .flags = flags, .pApplicationInfo = info, .enabledLayerCount = LayersN, @@ -155,92 +195,299 @@ public: .ppEnabledExtensionNames = nullptr, } { _layers.reserve(LayersN); - for (const auto& layer : layers) { _layers.push_back(layer); } + for (const auto& layer : layers) { + _layers.push_back(layer); + } _extensions.reserve(ExtensionsN); - for (const auto& extension : extensions) { _extensions.push_back(extension); } + for (const auto& extension : extensions) { + _extensions.push_back(extension); + } ppEnabledLayerNames = _layers.data(); ppEnabledExtensionNames = _extensions.data(); } + /// + /// \brief Dynamic Layer Constructor + /// \param flags The flags to create the instance with. + /// \param info A const-qualified reference to an \ref fennec::vk::app_info "app_info" object. + /// \param layers An array of layer names to enable. + /// + /// \note The object referenced by \emph{info} must have a lifetime that extends until an + /// \ref fennec::vk::instance "instance" is constructed. create_info( create_flags flags, const app_info& info, - const dynarray& layers, nullptr_t, - void* ext + const dynarray& layers, nullptr_t ) : VkInstanceCreateInfo { .sType = VK_STRUCTURE_TYPE_INSTANCE_CREATE_INFO, - .pNext = ext, + .pNext = nullptr, .flags = flags, .pApplicationInfo = info, - .enabledLayerCount = layers.size(), + .enabledLayerCount = static_cast(layers.size()), .ppEnabledLayerNames = nullptr, .enabledExtensionCount = 0, .ppEnabledExtensionNames = nullptr, } { _layers.reserve(enabledLayerCount); - for (const auto& layer : layers) { _layers.push_back(layer); } + for (const auto& layer : layers) { + _layers.push_back(layer); + } ppEnabledLayerNames = _layers.data(); ppEnabledExtensionNames = _extensions.data(); } + /// + /// \brief Dynamic Extension Constructor + /// \param flags The flags to create the instance with. + /// \param info A const-qualified reference to an \ref fennec::vk::app_info "app_info" object. + /// \param extensions An array of extension names to enable. + /// \param ext An extension structure. + /// + /// \note The object referenced by \emph{info} must have a lifetime that extends until an + /// \ref fennec::vk::instance "instance" is constructed. create_info( create_flags flags, const app_info& info, - nullptr_t, const dynarray& extensions, - void* ext + nullptr_t, const dynarray& extensions ) : VkInstanceCreateInfo { .sType = VK_STRUCTURE_TYPE_INSTANCE_CREATE_INFO, - .pNext = ext, + .pNext = nullptr, .flags = flags, .pApplicationInfo = info, .enabledLayerCount = 0, .ppEnabledLayerNames = nullptr, - .enabledExtensionCount = extensions.size(), + .enabledExtensionCount = static_cast(extensions.size()), .ppEnabledExtensionNames = nullptr, } { _extensions.reserve(enabledExtensionCount); - for (const auto& extension : extensions) { _extensions.push_back(extension); } + for (const auto& extension : extensions) { + _extensions.push_back(extension); + } ppEnabledLayerNames = _layers.data(); ppEnabledExtensionNames = _extensions.data(); } + /// + /// \brief Dynamic Layer-Extension Constructor + /// \param flags The flags to create the instance with. + /// \param info A const-qualified reference to an \ref fennec::vk::app_info "app_info" object. + /// \param layers An array of layer names to enable. + /// \param extensions An array of extension names to enable. + /// + /// \note The object referenced by \emph{info} must have a lifetime that extends until an + /// \ref fennec::vk::instance "instance" is constructed. create_info( create_flags flags, const app_info& info, - const dynarray& layers, const dynarray& extensions, - void* ext + const dynarray& layers, const dynarray& extensions ) : VkInstanceCreateInfo { .sType = VK_STRUCTURE_TYPE_INSTANCE_CREATE_INFO, - .pNext = ext, + .pNext = nullptr, .flags = flags, .pApplicationInfo = info, - .enabledLayerCount = layers.size(), + .enabledLayerCount = static_cast(layers.size()), .ppEnabledLayerNames = nullptr, - .enabledExtensionCount = extensions.size(), + .enabledExtensionCount = static_cast(extensions.size()), .ppEnabledExtensionNames = nullptr, } { _layers.reserve(enabledLayerCount); - for (const auto& layer : layers) { _layers.push_back(layer); } + for (const auto& layer : layers) { + _layers.push_back(layer); + } _extensions.reserve(enabledExtensionCount); - for (const auto& extension : extensions) { _extensions.push_back(extension); } + for (const auto& extension : extensions) { + _extensions.push_back(extension); + } ppEnabledLayerNames = _layers.data(); ppEnabledExtensionNames = _extensions.data(); } + /// + /// \brief Destructor + ~create_info() = default; + + /// @} + // Assignment ------------------------------------------------------------------------------------------------------ + public: + + /// \name Assignment + /// @{ + + /// + /// \brief Copy Assignment + /// \param rhs Create info to copy + /// \returns A reference to \emph{this} after having copied \emph{rhs} + create_info& operator=(const create_info& rhs) { + pNext = rhs.pNext; + flags = rhs.flags; + pApplicationInfo = rhs.pApplicationInfo; + + _layers = rhs._layers; + ppEnabledLayerNames = _layers.data(); + enabledLayerCount = _layers.size(); + + _extensions = rhs._extensions; + ppEnabledExtensionNames = _extensions.data(); + enabledExtensionCount = _extensions.size(); + + return *this; + } + + /// + /// \brief Move Assignment + /// \param rhs Create info to move + /// \returns A reference to \emph{this} after having taken ownership of \emph{rhs} + create_info& operator=(create_info&& rhs) noexcept { + pNext = rhs.pNext; + flags = rhs.flags; + pApplicationInfo = rhs.pApplicationInfo; + + _layers = move(rhs._layers); + ppEnabledLayerNames = _layers.data(); + enabledLayerCount = _layers.size(); + + _extensions = move(rhs._extensions); + ppEnabledExtensionNames = _extensions.data(); + enabledExtensionCount = _extensions.size(); + + return *this; + } + + /// @} + + + // Layers & Extensions --------------------------------------------------------------------------------------------- + public: + + /// \name Layers & Extensions + /// @{ + + /// + /// \brief Enable the specified layer. + /// \param layer The layer name to enable. + void enable_layer(const cstring& layer) { + _layers.emplace_back(layer.data()); + enabledLayerCount = _layers.size(); + ppEnabledLayerNames = _layers.data(); + } + + /// + /// \brief Enable the specified extension. + /// \param extension The extension name to enable. + void enable_extension(const cstring& extension) { + _extensions.emplace_back(extension.data()); + enabledExtensionCount = _extensions.size(); + ppEnabledExtensionNames = _extensions.data(); + } + + /// + /// \brief Attach a debugger. + /// \param dbg The debugger to attach. + void attach_debugger(const debugger& dbg) { + _info = make_unique(dbg); + pNext = *_info; + } + + /// @} + + + // Implicit Conversions -------------------------------------------------------------------------------------------- + public: + + /// \name Implicit Conversions + /// @{ + + /// + /// \returns \emph{this} as if it were a pointer to the underlying type, \emph{VkInstanceCreateInfo}. + operator VkInstanceCreateInfo*() noexcept { + return this; + } + + /// + /// \brief Implicit Pointer Conversion + /// \returns \emph{this} as if it were a pointer to the underlying type, \emph{VkInstanceCreateInfo}. + operator const VkInstanceCreateInfo*() const noexcept { + return this; + } + + /// @} + + + // Private Member Variables ---------------------------------------------------------------------------------------- private: dynarray _layers; dynarray _extensions; + unique_ptr _info; }; - instance(); + /// @} + private: - VkInstance _handle; + using device_list = dynarray; + + + +// Constructors & Destructor =========================================================================================== +public: + + /// \name Constructors & Destructor + /// @{ + + /// + /// \brief Instance Constructor + /// \param info The info to create the instance with. + /// \details Initializes a new \emph{VkInstance} using \emph{info}. + instance(const create_info& info) { + assertf((vkCreateInstance(info, nullptr, &_handle)), "Failed to create Vulkan instance."); + + uint32_t count = 0; + vkEnumeratePhysicalDevices(_handle, &count, nullptr); + dynarray devices(count); + vkEnumeratePhysicalDevices(_handle, &count, devices.data()); + + _devices = devices; + } + + /// + /// Copy Constructor + /// \details Deleted, no semantics for copying an instance + instance(const instance&) = delete; + + /// + /// \brief Instance Destructor + /// \details Cleans up the held \emph{VkInstance}. + ~instance() { + vkDestroyInstance(_handle, nullptr); + } + + /// @} + + + +// Properties ========================================================================================================== +public: + + const device_list& available_devices() const { + return _devices; + } + + +// Access ============================================================================================================== + + operator VkInstance() const { + return _handle; + } + +// Private Member Variables ============================================================================================ +private: + VkInstance _handle; + device_list _devices; }; } diff --git a/include/fennec/renderers/vulkan/lib/logical_device.h b/include/fennec/renderers/vulkan/lib/logical_device.h new file mode 100644 index 0000000..eec66dc --- /dev/null +++ b/include/fennec/renderers/vulkan/lib/logical_device.h @@ -0,0 +1,61 @@ +// ===================================================================================================================== +// fennec, a free and open source game engine +// Copyright © 2025 Medusa Slockbower +// +// This program is free software: you can redistribute it and/or modify +// it under the terms of the GNU General Public License as published by +// the Free Software Foundation, either version 3 of the License, or +// (at your option) any later version. +// +// This program is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. +// +// You should have received a copy of the GNU General Public License +// along with this program. If not, see . +// ===================================================================================================================== + +/// +/// \file logical_device.h +/// \brief +/// +/// +/// \details +/// \author Medusa Slockbower +/// +/// \copyright Copyright © 2025 - 2026 Medusa Slockbower ([GPLv3](https://www.gnu.org/licenses/gpl-3.0.en.html)) +/// +/// + + +#ifndef FENNEC_RENDERERS_VULKAN_LIB_LOGICAL_DEVICE_H +#define FENNEC_RENDERERS_VULKAN_LIB_LOGICAL_DEVICE_H +#include + +namespace fennec::vk +{ + +class logical_device { +public: + logical_device(physical_device& device) + : _physical(&device) { + + VkDeviceCreateInfo info { + + }; + + vkCreateDevice(_physical, ) + } + + const physical_device& physical() const { + return *_physical; + } + +private: + physical_device* _physical; +}; + +} + +#endif // FENNEC_RENDERERS_VULKAN_LIB_LOGICAL_DEVICE_H \ No newline at end of file diff --git a/include/fennec/renderers/vulkan/lib/physical_device.h b/include/fennec/renderers/vulkan/lib/physical_device.h new file mode 100644 index 0000000..7881ef0 --- /dev/null +++ b/include/fennec/renderers/vulkan/lib/physical_device.h @@ -0,0 +1,276 @@ +// ===================================================================================================================== +// fennec, a free and open source game engine +// Copyright © 2025 Medusa Slockbower +// +// This program is free software: you can redistribute it and/or modify +// it under the terms of the GNU General Public License as published by +// the Free Software Foundation, either version 3 of the License, or +// (at your option) any later version. +// +// This program is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. +// +// You should have received a copy of the GNU General Public License +// along with this program. If not, see . +// ===================================================================================================================== + +/// +/// \file physical_device.h +/// \brief +/// +/// +/// \details +/// \author Medusa Slockbower +/// +/// \copyright Copyright © 2025 - 2026 Medusa Slockbower ([GPLv3](https://www.gnu.org/licenses/gpl-3.0.en.html)) +/// +/// + + +#ifndef FENNEC_RENDERERS_VULKAN_LIB_PHYSICAL_DEVICE_H +#define FENNEC_RENDERERS_VULKAN_LIB_PHYSICAL_DEVICE_H + +#include +#include +#include + +#include +#include + +namespace fennec::vk +{ + + + + + +// Queue Families ====================================================================================================== + +/// +/// \brief Struct representing the queue families a device has available. +struct device_queue_families { +// Definitions --------------------------------------------------------------------------------------------------------- +private: + + using properties_t = dynarray; + using properties2_t = dynarray; + + +// Constructors & Destructor ------------------------------------------------------------------------------------------- +public: + + /// \name Constructors & Destructor + /// @{ + + /// + /// \brief Queue Families Constructor + /// \param device The device to obtain queue family information from. + explicit device_queue_families(VkPhysicalDevice device) + : _use_deprecated(vkGetPhysicalDeviceQueueFamilyProperties2 == nullptr) { + uint32_t count = 0; + if (_use_deprecated) { + vkGetPhysicalDeviceQueueFamilyProperties(device, &count, nullptr); + _queues2.resize(count); + vkGetPhysicalDeviceQueueFamilyProperties(device, &count, _queues.data()); + } else { + vkGetPhysicalDeviceQueueFamilyProperties2(device, &count, nullptr); + _queues2.resize(count); + vkGetPhysicalDeviceQueueFamilyProperties2(device, &count, _queues2.data()); + } + + // TODO: Extensions + } + + /// + /// \brief Destructor + ~device_queue_families() = default; + + /// @} + + +// Properties ---------------------------------------------------------------------------------------------------------- +public: + + /// \name Properties + /// @{ + + /// + /// \returns The number of queue families associated with the device. + size_t size() const { + return _use_deprecated ? _queues.size() : _queues2.size(); + } + + /// @} + + +// Access -------------------------------------------------------------------------------------------------------------- +public: + + /// \name Access + /// @{ + + /// + /// \brief Queue Properties Access. + /// \param i The index of the queue family. + /// \returns A reference to the properties of the specified queue family. + const VkQueueFamilyProperties& operator[](size_t i) const { + return _use_deprecated ? _queues[i] : _queues2[i].queueFamilyProperties; + } + + /// @} + + +// Private Member Variables -------------------------------------------------------------------------------------------- +private: + + bool _use_deprecated; + properties_t _queues; + properties2_t _queues2; +}; + + +// Physical Device ===================================================================================================== + +/// +/// \brief RAII Wrapper for VkPhysicalDevice. +/// \details Acquires information about the physical device at construction. +struct physical_device { +// Definitions --------------------------------------------------------------------------------------------------------- +public: + + /// \name Definitions + /// @{ + + using handle_t = VkPhysicalDevice; //!< The underlying handle type + + /// @} + + +// Constructors & Destructor ------------------------------------------------------------------------------------------- +public: + + /// \name Constructors & Destructor + /// @{ + + /// + /// \brief Device Constructor + /// \param handle The handle to acquire. + /// \details Acquires device information. + explicit physical_device(VkPhysicalDevice handle) + : _handle(handle) + , _properties(handle) + , _features(handle, _properties) + , _queue_families(handle) { } + + /// + /// \brief Move Constructor + /// \param device The device to acquire. + /// \details Moves already gathered information instead polling the driver again. + physical_device(physical_device&& device) noexcept + : _handle(device._handle) + , _properties(move(device._properties)) + , _features(move(device._features)) + , _queue_families(move(device._queue_families)) { } + + /// @} + + +// Assignment ---------------------------------------------------------------------------------------------------------- +public: + + /// + /// \brief Move Assignment + /// \param device + /// \return + physical_device& operator=(physical_device&& device) noexcept { + _handle = device._handle; + _properties = move(device._properties); + _features = move(device._features); + _queue_families = move(device._queue_families); + return *this; + } + + +// Properties ---------------------------------------------------------------------------------------------------------- +public: + + /// + /// \returns The API version supported by the device + version api_version() const { + return { + .major = VK_API_VERSION_MAJOR(_properties.core10->apiVersion), + .minor = VK_API_VERSION_MINOR(_properties.core10->apiVersion), + .patch = VK_API_VERSION_PATCH(_properties.core10->apiVersion), + .meta = VK_API_VERSION_VARIANT(_properties.core10->apiVersion), + }; + } + + /// + /// \returns The version of the device's driver + version driver_version() const { + return { + .major = VK_VERSION_MAJOR(_properties.core10->driverVersion), + .minor = VK_VERSION_MINOR(_properties.core10->driverVersion), + .patch = VK_VERSION_PATCH(_properties.core10->driverVersion), + }; + } + + /// + /// \returns The type of the device. + /// \see fennec::vk::device_type_ + uint32_t type() const { + return _properties.core10->deviceType; + } + + cstring name() const { + return _properties.core10->deviceName; + } + + const device_properties& properties() const { + return _properties; + } + + const device_features& features() const { + return _features; + } + + const device_queue_families& queue_families() const { + return _queue_families; + } + + uint32_t score() const { + uint32_t score = 0; + version api = api_version(); + score += 1000 * api.major + 100 * api.minor; + score += 1000 * _type_score(); + return score; + } + +// Private Member Variables -------------------------------------------------------------------------------------------- +private: + + handle_t _handle; + device_properties _properties; + device_features _features; + device_queue_families _queue_families; + + +// Private Helpers ----------------------------------------------------------------------------------------------------- +private: + + uint32_t _type_score() const { + switch (_properties.core10->deviceType) { + default: + case VK_PHYSICAL_DEVICE_TYPE_OTHER: return 1; + case VK_PHYSICAL_DEVICE_TYPE_CPU: return 2; + case VK_PHYSICAL_DEVICE_TYPE_VIRTUAL_GPU: return 3; + case VK_PHYSICAL_DEVICE_TYPE_INTEGRATED_GPU: return 4; + case VK_PHYSICAL_DEVICE_TYPE_DISCRETE_GPU: return 5; + } + } +}; +} + +#endif // FENNEC_RENDERERS_VULKAN_LIB_PHYSICAL_DEVICE_H diff --git a/include/fennec/renderers/vulkan/lib/physical_device_features.h b/include/fennec/renderers/vulkan/lib/physical_device_features.h new file mode 100644 index 0000000..f753e06 --- /dev/null +++ b/include/fennec/renderers/vulkan/lib/physical_device_features.h @@ -0,0 +1,3123 @@ +// ===================================================================================================================== +// fennec, a free and open source game engine +// Copyright © 2025 - 2026 Medusa Slockbower +// +// This program is free software: you can redistribute it and/or modify +// it under the terms of the GNU General Public License as published by +// the Free Software Foundation, either version 3 of the License, or +// (at your option) any later version. +// +// This program is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. +// +// You should have received a copy of the GNU General Public License +// along with this program. If not, see . +// ===================================================================================================================== + +/// +/// \file fennec/renderers/vulkan/lib/physical_device_features.h +/// \brief +/// +/// +/// \details +/// \author Medusa Slockbower +/// +/// \copyright Copyright © 2025 Medusa Slockbower ([GPLv3](https://www.gnu.org/licenses/gpl-3.0.en.html)) +/// +/// + + +#ifndef FENNEC_RENDERERS_VULKAN_LIB_PHYSICAL_DEVICE_FEATURES_H +#define FENNEC_RENDERERS_VULKAN_LIB_PHYSICAL_DEVICE_FEATURES_H + +#include + +#include + +namespace fennec::vk +{ + +// Device Features ===================================================================================================== + +/// +/// \brief Core 1.1 Features +struct device_features_11 : private VkPhysicalDeviceVulkan11Features, + + // Vulkan 1.1 Features + private VkPhysicalDevice16BitStorageFeatures, + private VkPhysicalDeviceMultiviewFeatures, + private VkPhysicalDeviceVariablePointersFeatures, + private VkPhysicalDeviceProtectedMemoryFeatures, + private VkPhysicalDeviceSamplerYcbcrConversionFeatures, + private VkPhysicalDeviceShaderDrawParametersFeatures { + +// Public References --------------------------------------------------------------------------------------------------- +public: + + /// \name Features + /// @{ + + VkBool32* storageBuffer16BitAccess; //!< Storage Buffer 16-Bit Access + VkBool32* uniformAndStorageBuffer16BitAccess; //!< Uniform And Storage Buffer 16-Bit Access + VkBool32* storagePushConstant16; //!< Storage Push Constant 16 + VkBool32* storageInputOutput16; //!< Storage Input Output 16 + VkBool32* multiview; //!< Multiview + VkBool32* multiviewGeometryShader; //!< Multiview Geometry Shader + VkBool32* multiviewTessellationShader; //!< Multiview Tessellation Shader + VkBool32* variablePointersStorageBuffer; //!< Variable Pointers Storage Buffer + VkBool32* variablePointers; //!< Variable Pointers + VkBool32* protectedMemory; //!< Protected Memory + VkBool32* samplerYcbcrConversion; //!< Sampler Ycbcr Conversion + VkBool32* shaderDrawParameters; //!< Shader Draw Parameters + VkBool32 useCore; //!< Use Core + + /// @} + + +// Methods ------------------------------------------------------------------------------------------------------------- +public: + + /// + /// \brief Default Constructor + /// \details Version information is necessary for this structure to fill itself in properly, so the default + /// constructor is not allowed. + device_features_11() = delete; + + /// + /// \brief Features Constructor + /// \param properties Properties structure to poll necessary information + device_features_11(const device_properties& properties) + : VkPhysicalDeviceVulkan11Features { } + , VkPhysicalDevice16BitStorageFeatures { } + , VkPhysicalDeviceMultiviewFeatures { } + , VkPhysicalDeviceVariablePointersFeatures { } + , VkPhysicalDeviceProtectedMemoryFeatures { } + , VkPhysicalDeviceSamplerYcbcrConversionFeatures { } + , VkPhysicalDeviceShaderDrawParametersFeatures { } + , storageBuffer16BitAccess { nullptr } + , uniformAndStorageBuffer16BitAccess { nullptr } + , storagePushConstant16 { nullptr } + , storageInputOutput16 { nullptr } + , multiview { nullptr } + , multiviewGeometryShader { nullptr } + , multiviewTessellationShader { nullptr } + , variablePointersStorageBuffer { nullptr } + , variablePointers { nullptr } + , protectedMemory { nullptr } + , samplerYcbcrConversion { nullptr } + , shaderDrawParameters { nullptr } + , useCore { properties.core10->apiVersion >= VK_API_VERSION_1_1 } { + + _clear(); + _link(); + + } + + /// + /// \brief Copy Constructor + /// \param features The features structure to copy + device_features_11(const device_features_11& features) + : VkPhysicalDeviceVulkan11Features { features } + , VkPhysicalDevice16BitStorageFeatures { features } + , VkPhysicalDeviceMultiviewFeatures { features } + , VkPhysicalDeviceVariablePointersFeatures { features } + , VkPhysicalDeviceProtectedMemoryFeatures { features } + , VkPhysicalDeviceSamplerYcbcrConversionFeatures { features } + , VkPhysicalDeviceShaderDrawParametersFeatures { features } + , storageBuffer16BitAccess { nullptr } + , uniformAndStorageBuffer16BitAccess { nullptr } + , storagePushConstant16 { nullptr } + , storageInputOutput16 { nullptr } + , multiview { nullptr } + , multiviewGeometryShader { nullptr } + , multiviewTessellationShader { nullptr } + , variablePointersStorageBuffer { nullptr } + , variablePointers { nullptr } + , protectedMemory { nullptr } + , samplerYcbcrConversion { nullptr } + , shaderDrawParameters { nullptr } + , useCore { features.useCore } { + + _link(); + } + + /// + /// \brief Copy Assignment + /// \param features The features to copy + /// \returns A reference to \emph{this} + device_features_11& operator=(const device_features_11& features) { + if (this == &features) { + return *this; + } + + // Copy data + VkPhysicalDeviceVulkan11Features::operator=(features); + VkPhysicalDevice16BitStorageFeatures::operator=(features); + VkPhysicalDeviceMultiviewFeatures::operator=(features); + VkPhysicalDeviceVariablePointersFeatures::operator=(features); + VkPhysicalDeviceProtectedMemoryFeatures::operator=(features); + VkPhysicalDeviceSamplerYcbcrConversionFeatures::operator=(features); + VkPhysicalDeviceShaderDrawParametersFeatures::operator=(features); + useCore = features.useCore; + + _link(); + + return *this; + } + + /// + /// \brief Chain an extension structure + /// \param next + void chain(void* next) { + if (useCore) { + VkPhysicalDeviceVulkan11Features::pNext = next; + } else { + VkPhysicalDeviceShaderDrawParametersFeatures::pNext = next; + } + } + + /// + /// \brief Implicit casting for chaining + operator void*() { + if (useCore) { + return static_cast(this); + } else { + return static_cast(this); + } + } + + +// Helpers ------------------------------------------------------------------------------------------------------------- +private: + + void _clear() { + // Clear out the struct + fennec::memset(this, 0, sizeof(*this)); + + // Set the structure types + VkPhysicalDeviceVulkan11Features::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_VULKAN_1_1_FEATURES; + VkPhysicalDevice16BitStorageFeatures::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_16BIT_STORAGE_FEATURES; + VkPhysicalDeviceMultiviewFeatures::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_MULTIVIEW_FEATURES; + VkPhysicalDeviceVariablePointersFeatures::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_VARIABLE_POINTERS_FEATURES; + VkPhysicalDeviceProtectedMemoryFeatures::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_PROTECTED_MEMORY_FEATURES; + VkPhysicalDeviceSamplerYcbcrConversionFeatures::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SAMPLER_YCBCR_CONVERSION_FEATURES; + VkPhysicalDeviceShaderDrawParametersFeatures::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SHADER_DRAW_PARAMETERS_FEATURES; + } + + void _link() { + + // Check if we are Version 1.1 or later + if (useCore) { + + // Link to core structure + storageBuffer16BitAccess = &(VkPhysicalDeviceVulkan11Features::storageBuffer16BitAccess); + uniformAndStorageBuffer16BitAccess = &(VkPhysicalDeviceVulkan11Features::uniformAndStorageBuffer16BitAccess); + storagePushConstant16 = &(VkPhysicalDeviceVulkan11Features::storagePushConstant16); + storageInputOutput16 = &(VkPhysicalDeviceVulkan11Features::storageInputOutput16); + multiview = &(VkPhysicalDeviceVulkan11Features::multiview); + multiviewGeometryShader = &(VkPhysicalDeviceVulkan11Features::multiviewGeometryShader); + multiviewTessellationShader = &(VkPhysicalDeviceVulkan11Features::multiviewTessellationShader); + variablePointersStorageBuffer = &(VkPhysicalDeviceVulkan11Features::variablePointersStorageBuffer); + variablePointers = &(VkPhysicalDeviceVulkan11Features::variablePointers); + protectedMemory = &(VkPhysicalDeviceVulkan11Features::protectedMemory); + samplerYcbcrConversion = &(VkPhysicalDeviceVulkan11Features::samplerYcbcrConversion); + shaderDrawParameters = &(VkPhysicalDeviceVulkan11Features::shaderDrawParameters); + + VkPhysicalDeviceVulkan11Features::pNext = nullptr; + + return; + } + + + // Link to features structures + storageBuffer16BitAccess = &(VkPhysicalDevice16BitStorageFeatures::storageBuffer16BitAccess); + uniformAndStorageBuffer16BitAccess = &(VkPhysicalDevice16BitStorageFeatures::uniformAndStorageBuffer16BitAccess); + storagePushConstant16 = &(VkPhysicalDevice16BitStorageFeatures::storagePushConstant16); + storageInputOutput16 = &(VkPhysicalDevice16BitStorageFeatures::storageInputOutput16); + multiview = &(VkPhysicalDeviceMultiviewFeatures::multiview); + multiviewGeometryShader = &(VkPhysicalDeviceMultiviewFeatures::multiviewGeometryShader); + multiviewTessellationShader = &(VkPhysicalDeviceMultiviewFeatures::multiviewTessellationShader); + variablePointersStorageBuffer = &(VkPhysicalDeviceVariablePointersFeatures::variablePointersStorageBuffer); + variablePointers = &(VkPhysicalDeviceVariablePointersFeatures::variablePointers); + protectedMemory = &(VkPhysicalDeviceProtectedMemoryFeatures::protectedMemory); + samplerYcbcrConversion = &(VkPhysicalDeviceSamplerYcbcrConversionFeatures::samplerYcbcrConversion); + shaderDrawParameters = &(VkPhysicalDeviceShaderDrawParametersFeatures::shaderDrawParameters); + + + // Daisy chain + VkPhysicalDevice16BitStorageFeatures::pNext = static_cast(this); + VkPhysicalDeviceMultiviewFeatures::pNext = static_cast(this); + VkPhysicalDeviceVariablePointersFeatures::pNext = static_cast(this); + VkPhysicalDeviceProtectedMemoryFeatures::pNext = static_cast(this); + VkPhysicalDeviceSamplerYcbcrConversionFeatures::pNext = static_cast(this); + VkPhysicalDeviceShaderDrawParametersFeatures::pNext = nullptr; + } +}; + +/// +/// \brief Core 1.2 Features +struct device_features_12 : private VkPhysicalDeviceVulkan12Features, + private VkPhysicalDevice8BitStorageFeatures, + private VkPhysicalDeviceShaderAtomicInt64Features, + private VkPhysicalDeviceShaderFloat16Int8Features, + private VkPhysicalDeviceDescriptorIndexingFeatures, + private VkPhysicalDeviceScalarBlockLayoutFeatures, + private VkPhysicalDeviceImagelessFramebufferFeatures, + private VkPhysicalDeviceUniformBufferStandardLayoutFeatures, + private VkPhysicalDeviceShaderSubgroupExtendedTypesFeatures, + private VkPhysicalDeviceSeparateDepthStencilLayoutsFeatures, + private VkPhysicalDeviceHostQueryResetFeatures, + private VkPhysicalDeviceTimelineSemaphoreFeatures, + private VkPhysicalDeviceBufferDeviceAddressFeatures, + private VkPhysicalDeviceVulkanMemoryModelFeatures { + +// Public References --------------------------------------------------------------------------------------------------- +public: + + /// \name Features + /// @{ + + VkBool32* samplerMirrorClampToEdge; //!< Sampler Mirror Clamp To Edge + VkBool32* drawIndirectCount; //!< Draw Indirect Count + VkBool32* storageBuffer8BitAccess; //!< Storage Buffer 8-Bit Access + VkBool32* uniformAndStorageBuffer8BitAccess; //!< Uniform And Storage Buffer 8-Bit Access + VkBool32* storagePushConstant8; //!< Storage Push Constant 8 + VkBool32* shaderBufferInt64Atomics; //!< Shader Buffer Int64 Atomics + VkBool32* shaderSharedInt64Atomics; //!< Shader Shared Int64 Atomics + VkBool32* shaderFloat16; //!< Shader Float16 + VkBool32* shaderInt8; //!< Shader Int8 + VkBool32* descriptorIndexing; //!< Descriptor Indexing + VkBool32* shaderInputAttachmentArrayDynamicIndexing; //!< Shader Input Attachment Array Dynamic Indexing + VkBool32* shaderUniformTexelBufferArrayDynamicIndexing; //!< Shader Uniform Texel Buffer Array Dynamic Indexing + VkBool32* shaderStorageTexelBufferArrayDynamicIndexing; //!< Shader Storage Texel Buffer Array Dynamic Indexing + VkBool32* shaderUniformBufferArrayNonUniformIndexing; //!< Shader Uniform Buffer Array Non-Uniform Indexing + VkBool32* shaderSampledImageArrayNonUniformIndexing; //!< Shader Sampled Image Array Non-Uniform Indexing + VkBool32* shaderStorageBufferArrayNonUniformIndexing; //!< Shader Storage Buffer Array Non-Uniform Indexing + VkBool32* shaderStorageImageArrayNonUniformIndexing; //!< Shader Storage Image Array Non-Uniform Indexing + VkBool32* shaderInputAttachmentArrayNonUniformIndexing; //!< Shader Input Attachment Array Non-Uniform Indexing + VkBool32* shaderUniformTexelBufferArrayNonUniformIndexing; //!< Shader Uniform Texel Buffer Array Non-Uniform Indexing + VkBool32* shaderStorageTexelBufferArrayNonUniformIndexing; //!< Shader Storage Texel Buffer Array Non-Uniform Indexing + VkBool32* descriptorBindingUniformBufferUpdateAfterBind; //!< Descriptor Binding Uniform Buffer Update After Bind + VkBool32* descriptorBindingSampledImageUpdateAfterBind; //!< Descriptor Binding Sampled Image Update After Bind + VkBool32* descriptorBindingStorageImageUpdateAfterBind; //!< Descriptor Binding Storage Image Update After Bind + VkBool32* descriptorBindingStorageBufferUpdateAfterBind; //!< Descriptor Binding Storage Buffer Update After Bind + VkBool32* descriptorBindingUniformTexelBufferUpdateAfterBind; //!< Descriptor Binding Uniform Texel Buffer Update After Bind + VkBool32* descriptorBindingStorageTexelBufferUpdateAfterBind; //!< Descriptor Binding Storage Texel Buffer Update After Bind + VkBool32* descriptorBindingUpdateUnusedWhilePending; //!< Descriptor Binding Update Unused While Pending + VkBool32* descriptorBindingPartiallyBound; //!< Descriptor Binding Partially Bound + VkBool32* descriptorBindingVariableDescriptorCount; //!< Descriptor Binding Variable Descriptor Count + VkBool32* runtimeDescriptorArray; //!< Runtime Descriptor Array + VkBool32* samplerFilterMinmax; //!< Sampler Filter Minmax + VkBool32* scalarBlockLayout; //!< Scalar Block Layout + VkBool32* imagelessFramebuffer; //!< Imageless Framebuffer + VkBool32* uniformBufferStandardLayout; //!< Uniform Buffer Standard Layout + VkBool32* shaderSubgroupExtendedTypes; //!< Shader Subgroup Extended Types + VkBool32* separateDepthStencilLayouts; //!< Separate Depth Stencil Layouts + VkBool32* hostQueryReset; //!< Host Query Reset + VkBool32* timelineSemaphore; //!< Timeline Semaphore + VkBool32* bufferDeviceAddress; //!< Buffer Device Address + VkBool32* bufferDeviceAddressCaptureReplay; //!< Buffer Device Address Capture Replay + VkBool32* bufferDeviceAddressMultiDevice; //!< Buffer Device Address Multi Device + VkBool32* vulkanMemoryModel; //!< Vulkan Memory Model + VkBool32* vulkanMemoryModelDeviceScope; //!< Vulkan Memory Model Device Scope + VkBool32* vulkanMemoryModelAvailabilityVisibilityChains; //!< Vulkan Memory Model Availability Visibility Chains + VkBool32* shaderOutputViewportIndex; //!< Shader Output Viewport Index + VkBool32* shaderOutputLayer; //!< Shader Output Layer + VkBool32* subgroupBroadcastDynamicId; //!< Subgroup Broadcast Dynamic ID + VkBool32 useCore; //!< Use Core + + /// @} + + +// Methods ------------------------------------------------------------------------------------------------------------- +public: + + /// + /// \brief Default Constructor + /// \details Version information is necessary for this structure to fill itself in properly, so the default + /// constructor is not allowed. + device_features_12() = delete; + + /// + /// \brief Features Constructor + /// \param properties Properties structure to poll necessary information + device_features_12(const device_properties& properties) + : VkPhysicalDeviceVulkan12Features { } + , VkPhysicalDevice8BitStorageFeatures { } + , VkPhysicalDeviceShaderAtomicInt64Features { } + , VkPhysicalDeviceShaderFloat16Int8Features { } + , VkPhysicalDeviceDescriptorIndexingFeatures { } + , VkPhysicalDeviceScalarBlockLayoutFeatures { } + , VkPhysicalDeviceImagelessFramebufferFeatures { } + , VkPhysicalDeviceUniformBufferStandardLayoutFeatures { } + , VkPhysicalDeviceShaderSubgroupExtendedTypesFeatures { } + , VkPhysicalDeviceSeparateDepthStencilLayoutsFeatures { } + , VkPhysicalDeviceHostQueryResetFeatures { } + , VkPhysicalDeviceTimelineSemaphoreFeatures { } + , VkPhysicalDeviceBufferDeviceAddressFeatures { } + , VkPhysicalDeviceVulkanMemoryModelFeatures { } + , samplerMirrorClampToEdge { nullptr } + , drawIndirectCount { nullptr } + , storageBuffer8BitAccess { nullptr } + , uniformAndStorageBuffer8BitAccess { nullptr } + , storagePushConstant8 { nullptr } + , shaderBufferInt64Atomics { nullptr } + , shaderSharedInt64Atomics { nullptr } + , shaderFloat16 { nullptr } + , shaderInt8 { nullptr } + , descriptorIndexing { nullptr } + , shaderInputAttachmentArrayDynamicIndexing { nullptr } + , shaderUniformTexelBufferArrayDynamicIndexing { nullptr } + , shaderStorageTexelBufferArrayDynamicIndexing { nullptr } + , shaderUniformBufferArrayNonUniformIndexing { nullptr } + , shaderSampledImageArrayNonUniformIndexing { nullptr } + , shaderStorageBufferArrayNonUniformIndexing { nullptr } + , shaderStorageImageArrayNonUniformIndexing { nullptr } + , shaderInputAttachmentArrayNonUniformIndexing { nullptr } + , shaderUniformTexelBufferArrayNonUniformIndexing { nullptr } + , shaderStorageTexelBufferArrayNonUniformIndexing { nullptr } + , descriptorBindingUniformBufferUpdateAfterBind { nullptr } + , descriptorBindingSampledImageUpdateAfterBind { nullptr } + , descriptorBindingStorageImageUpdateAfterBind { nullptr } + , descriptorBindingStorageBufferUpdateAfterBind { nullptr } + , descriptorBindingUniformTexelBufferUpdateAfterBind { nullptr } + , descriptorBindingStorageTexelBufferUpdateAfterBind { nullptr } + , descriptorBindingUpdateUnusedWhilePending { nullptr } + , descriptorBindingPartiallyBound { nullptr } + , descriptorBindingVariableDescriptorCount { nullptr } + , runtimeDescriptorArray { nullptr } + , samplerFilterMinmax { nullptr } + , scalarBlockLayout { nullptr } + , imagelessFramebuffer { nullptr } + , uniformBufferStandardLayout { nullptr } + , shaderSubgroupExtendedTypes { nullptr } + , separateDepthStencilLayouts { nullptr } + , hostQueryReset { nullptr } + , timelineSemaphore { nullptr } + , bufferDeviceAddress { nullptr } + , bufferDeviceAddressCaptureReplay { nullptr } + , bufferDeviceAddressMultiDevice { nullptr } + , vulkanMemoryModel { nullptr } + , vulkanMemoryModelDeviceScope { nullptr } + , vulkanMemoryModelAvailabilityVisibilityChains { nullptr } + , shaderOutputViewportIndex { nullptr } + , shaderOutputLayer { nullptr } + , subgroupBroadcastDynamicId { nullptr } + , useCore { properties.core10->apiVersion >= VK_API_VERSION_1_2 } { + + _clear(); + _link(); + } + + /// + /// \brief Copy Constructor + /// \param features The features structure to copy + device_features_12(const device_features_12& features) + : VkPhysicalDeviceVulkan12Features { features } + , VkPhysicalDevice8BitStorageFeatures { features } + , VkPhysicalDeviceShaderAtomicInt64Features { features } + , VkPhysicalDeviceShaderFloat16Int8Features { features } + , VkPhysicalDeviceDescriptorIndexingFeatures { features } + , VkPhysicalDeviceScalarBlockLayoutFeatures { features } + , VkPhysicalDeviceImagelessFramebufferFeatures { features } + , VkPhysicalDeviceUniformBufferStandardLayoutFeatures { features } + , VkPhysicalDeviceShaderSubgroupExtendedTypesFeatures { features } + , VkPhysicalDeviceSeparateDepthStencilLayoutsFeatures { features } + , VkPhysicalDeviceHostQueryResetFeatures { features } + , VkPhysicalDeviceTimelineSemaphoreFeatures { features } + , VkPhysicalDeviceBufferDeviceAddressFeatures { features } + , VkPhysicalDeviceVulkanMemoryModelFeatures { features } + , samplerMirrorClampToEdge { nullptr } + , drawIndirectCount { nullptr } + , storageBuffer8BitAccess { nullptr } + , uniformAndStorageBuffer8BitAccess { nullptr } + , storagePushConstant8 { nullptr } + , shaderBufferInt64Atomics { nullptr } + , shaderSharedInt64Atomics { nullptr } + , shaderFloat16 { nullptr } + , shaderInt8 { nullptr } + , descriptorIndexing { nullptr } + , shaderInputAttachmentArrayDynamicIndexing { nullptr } + , shaderUniformTexelBufferArrayDynamicIndexing { nullptr } + , shaderStorageTexelBufferArrayDynamicIndexing { nullptr } + , shaderUniformBufferArrayNonUniformIndexing { nullptr } + , shaderSampledImageArrayNonUniformIndexing { nullptr } + , shaderStorageBufferArrayNonUniformIndexing { nullptr } + , shaderStorageImageArrayNonUniformIndexing { nullptr } + , shaderInputAttachmentArrayNonUniformIndexing { nullptr } + , shaderUniformTexelBufferArrayNonUniformIndexing { nullptr } + , shaderStorageTexelBufferArrayNonUniformIndexing { nullptr } + , descriptorBindingUniformBufferUpdateAfterBind { nullptr } + , descriptorBindingSampledImageUpdateAfterBind { nullptr } + , descriptorBindingStorageImageUpdateAfterBind { nullptr } + , descriptorBindingStorageBufferUpdateAfterBind { nullptr } + , descriptorBindingUniformTexelBufferUpdateAfterBind { nullptr } + , descriptorBindingStorageTexelBufferUpdateAfterBind { nullptr } + , descriptorBindingUpdateUnusedWhilePending { nullptr } + , descriptorBindingPartiallyBound { nullptr } + , descriptorBindingVariableDescriptorCount { nullptr } + , runtimeDescriptorArray { nullptr } + , samplerFilterMinmax { nullptr } + , scalarBlockLayout { nullptr } + , imagelessFramebuffer { nullptr } + , uniformBufferStandardLayout { nullptr } + , shaderSubgroupExtendedTypes { nullptr } + , separateDepthStencilLayouts { nullptr } + , hostQueryReset { nullptr } + , timelineSemaphore { nullptr } + , bufferDeviceAddress { nullptr } + , bufferDeviceAddressCaptureReplay { nullptr } + , bufferDeviceAddressMultiDevice { nullptr } + , vulkanMemoryModel { nullptr } + , vulkanMemoryModelDeviceScope { nullptr } + , vulkanMemoryModelAvailabilityVisibilityChains { nullptr } + , shaderOutputViewportIndex { nullptr } + , shaderOutputLayer { nullptr } + , subgroupBroadcastDynamicId { nullptr } + , useCore { features.useCore } { + + _link(); + } + + /// + /// \brief Copy Constructor + /// \param features The features structure to copy + /// \returns A reference to \emph{self} + device_features_12& operator=(const device_features_12& features) { + if (this == &features) { + return *this; + } + + // Copy data + VkPhysicalDeviceVulkan12Features::operator=(features); + VkPhysicalDevice8BitStorageFeatures::operator=(features); + VkPhysicalDeviceShaderAtomicInt64Features::operator=(features); + VkPhysicalDeviceShaderFloat16Int8Features::operator=(features); + VkPhysicalDeviceDescriptorIndexingFeatures::operator=(features); + VkPhysicalDeviceScalarBlockLayoutFeatures::operator=(features); + VkPhysicalDeviceImagelessFramebufferFeatures::operator=(features); + VkPhysicalDeviceUniformBufferStandardLayoutFeatures::operator=(features); + VkPhysicalDeviceShaderSubgroupExtendedTypesFeatures::operator=(features); + VkPhysicalDeviceSeparateDepthStencilLayoutsFeatures::operator=(features); + VkPhysicalDeviceHostQueryResetFeatures::operator=(features); + VkPhysicalDeviceTimelineSemaphoreFeatures::operator=(features); + VkPhysicalDeviceBufferDeviceAddressFeatures::operator=(features); + VkPhysicalDeviceVulkanMemoryModelFeatures::operator=(features); + useCore = features.useCore; + + _link(); + + return *this; + } + + /// + /// \brief Chain an extension structure + /// \param next + void chain(void* next) { + if (useCore) { + VkPhysicalDeviceVulkan12Features::pNext = next; + } else { + VkPhysicalDeviceVulkanMemoryModelFeatures::pNext = next; + } + } + + /// + /// \brief Implicit casting for chaining + operator void*() { + if (useCore) { + return static_cast(this); + } else { + return static_cast(this); + } + } + + +// Helpers ------------------------------------------------------------------------------------------------------------- +private: + + void _clear() { + + // Clear out the struct + fennec::memset(this, 0, sizeof(*this)); + + // Set structure types + VkPhysicalDeviceVulkan12Features::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_VULKAN_1_2_FEATURES; + VkPhysicalDevice8BitStorageFeatures::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_8BIT_STORAGE_FEATURES; + VkPhysicalDeviceShaderAtomicInt64Features::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SHADER_ATOMIC_INT64_FEATURES; + VkPhysicalDeviceShaderFloat16Int8Features::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SHADER_FLOAT16_INT8_FEATURES; + VkPhysicalDeviceDescriptorIndexingFeatures::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_DESCRIPTOR_INDEXING_FEATURES; + VkPhysicalDeviceScalarBlockLayoutFeatures::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SCALAR_BLOCK_LAYOUT_FEATURES; + VkPhysicalDeviceImagelessFramebufferFeatures::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_IMAGELESS_FRAMEBUFFER_FEATURES; + VkPhysicalDeviceUniformBufferStandardLayoutFeatures::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_UNIFORM_BUFFER_STANDARD_LAYOUT_FEATURES; + VkPhysicalDeviceShaderSubgroupExtendedTypesFeatures::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SHADER_SUBGROUP_EXTENDED_TYPES_FEATURES; + VkPhysicalDeviceSeparateDepthStencilLayoutsFeatures::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SEPARATE_DEPTH_STENCIL_LAYOUTS_FEATURES; + VkPhysicalDeviceHostQueryResetFeatures::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_HOST_QUERY_RESET_FEATURES; + VkPhysicalDeviceTimelineSemaphoreFeatures::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_TIMELINE_SEMAPHORE_FEATURES; + VkPhysicalDeviceBufferDeviceAddressFeatures::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_BUFFER_DEVICE_ADDRESS_FEATURES; + VkPhysicalDeviceVulkanMemoryModelFeatures::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_VULKAN_MEMORY_MODEL_FEATURES; + } + + void _link() { + + + + // Check if we are Version 1.2 or later. + if (useCore) { + + // Link to Core structure + samplerMirrorClampToEdge = &(VkPhysicalDeviceVulkan12Features::samplerMirrorClampToEdge); + drawIndirectCount = &(VkPhysicalDeviceVulkan12Features::drawIndirectCount); + storageBuffer8BitAccess = &(VkPhysicalDeviceVulkan12Features::storageBuffer8BitAccess); + uniformAndStorageBuffer8BitAccess = &(VkPhysicalDeviceVulkan12Features::uniformAndStorageBuffer8BitAccess); + storagePushConstant8 = &(VkPhysicalDeviceVulkan12Features::storagePushConstant8); + shaderBufferInt64Atomics = &(VkPhysicalDeviceVulkan12Features::shaderBufferInt64Atomics); + shaderSharedInt64Atomics = &(VkPhysicalDeviceVulkan12Features::shaderSharedInt64Atomics); + shaderFloat16 = &(VkPhysicalDeviceVulkan12Features::shaderFloat16); + shaderInt8 = &(VkPhysicalDeviceVulkan12Features::shaderInt8); + descriptorIndexing = &(VkPhysicalDeviceVulkan12Features::descriptorIndexing); + shaderInputAttachmentArrayDynamicIndexing = &(VkPhysicalDeviceVulkan12Features::shaderInputAttachmentArrayDynamicIndexing); + shaderUniformTexelBufferArrayDynamicIndexing = &(VkPhysicalDeviceVulkan12Features::shaderUniformTexelBufferArrayDynamicIndexing); + shaderStorageTexelBufferArrayDynamicIndexing = &(VkPhysicalDeviceVulkan12Features::shaderStorageTexelBufferArrayDynamicIndexing); + shaderUniformBufferArrayNonUniformIndexing = &(VkPhysicalDeviceVulkan12Features::shaderUniformBufferArrayNonUniformIndexing); + shaderSampledImageArrayNonUniformIndexing = &(VkPhysicalDeviceVulkan12Features::shaderSampledImageArrayNonUniformIndexing); + shaderStorageBufferArrayNonUniformIndexing = &(VkPhysicalDeviceVulkan12Features::shaderStorageBufferArrayNonUniformIndexing); + shaderStorageImageArrayNonUniformIndexing = &(VkPhysicalDeviceVulkan12Features::shaderStorageImageArrayNonUniformIndexing); + shaderInputAttachmentArrayNonUniformIndexing = &(VkPhysicalDeviceVulkan12Features::shaderInputAttachmentArrayNonUniformIndexing); + shaderUniformTexelBufferArrayNonUniformIndexing = &(VkPhysicalDeviceVulkan12Features::shaderUniformTexelBufferArrayNonUniformIndexing); + shaderStorageTexelBufferArrayNonUniformIndexing = &(VkPhysicalDeviceVulkan12Features::shaderStorageTexelBufferArrayNonUniformIndexing); + descriptorBindingUniformBufferUpdateAfterBind = &(VkPhysicalDeviceVulkan12Features::descriptorBindingUniformBufferUpdateAfterBind); + descriptorBindingSampledImageUpdateAfterBind = &(VkPhysicalDeviceVulkan12Features::descriptorBindingSampledImageUpdateAfterBind); + descriptorBindingStorageImageUpdateAfterBind = &(VkPhysicalDeviceVulkan12Features::descriptorBindingStorageImageUpdateAfterBind); + descriptorBindingStorageBufferUpdateAfterBind = &(VkPhysicalDeviceVulkan12Features::descriptorBindingStorageBufferUpdateAfterBind); + descriptorBindingUniformTexelBufferUpdateAfterBind = &(VkPhysicalDeviceVulkan12Features::descriptorBindingUniformTexelBufferUpdateAfterBind); + descriptorBindingStorageTexelBufferUpdateAfterBind = &(VkPhysicalDeviceVulkan12Features::descriptorBindingStorageTexelBufferUpdateAfterBind); + descriptorBindingUpdateUnusedWhilePending = &(VkPhysicalDeviceVulkan12Features::descriptorBindingUpdateUnusedWhilePending); + descriptorBindingPartiallyBound = &(VkPhysicalDeviceVulkan12Features::descriptorBindingPartiallyBound); + descriptorBindingVariableDescriptorCount = &(VkPhysicalDeviceVulkan12Features::descriptorBindingVariableDescriptorCount); + runtimeDescriptorArray = &(VkPhysicalDeviceVulkan12Features::runtimeDescriptorArray); + samplerFilterMinmax = &(VkPhysicalDeviceVulkan12Features::samplerFilterMinmax); + scalarBlockLayout = &(VkPhysicalDeviceVulkan12Features::scalarBlockLayout); + imagelessFramebuffer = &(VkPhysicalDeviceVulkan12Features::imagelessFramebuffer); + uniformBufferStandardLayout = &(VkPhysicalDeviceVulkan12Features::uniformBufferStandardLayout); + shaderSubgroupExtendedTypes = &(VkPhysicalDeviceVulkan12Features::shaderSubgroupExtendedTypes); + separateDepthStencilLayouts = &(VkPhysicalDeviceVulkan12Features::separateDepthStencilLayouts); + hostQueryReset = &(VkPhysicalDeviceVulkan12Features::hostQueryReset); + timelineSemaphore = &(VkPhysicalDeviceVulkan12Features::timelineSemaphore); + bufferDeviceAddress = &(VkPhysicalDeviceVulkan12Features::bufferDeviceAddress); + bufferDeviceAddressCaptureReplay = &(VkPhysicalDeviceVulkan12Features::bufferDeviceAddressCaptureReplay); + bufferDeviceAddressMultiDevice = &(VkPhysicalDeviceVulkan12Features::bufferDeviceAddressMultiDevice); + vulkanMemoryModel = &(VkPhysicalDeviceVulkan12Features::vulkanMemoryModel); + vulkanMemoryModelDeviceScope = &(VkPhysicalDeviceVulkan12Features::vulkanMemoryModelDeviceScope); + vulkanMemoryModelAvailabilityVisibilityChains = &(VkPhysicalDeviceVulkan12Features::vulkanMemoryModelAvailabilityVisibilityChains); + shaderOutputViewportIndex = &(VkPhysicalDeviceVulkan12Features::shaderOutputViewportIndex); + shaderOutputLayer = &(VkPhysicalDeviceVulkan12Features::shaderOutputLayer); + subgroupBroadcastDynamicId = &(VkPhysicalDeviceVulkan12Features::subgroupBroadcastDynamicId); + + VkPhysicalDeviceVulkan12Features::pNext = nullptr; + + return; + } + + + // Link to Feature structures + storageBuffer8BitAccess = &(VkPhysicalDevice8BitStorageFeatures::storageBuffer8BitAccess); + uniformAndStorageBuffer8BitAccess = &(VkPhysicalDevice8BitStorageFeatures::uniformAndStorageBuffer8BitAccess); + storagePushConstant8 = &(VkPhysicalDevice8BitStorageFeatures::storagePushConstant8); + shaderBufferInt64Atomics = &(VkPhysicalDeviceShaderAtomicInt64Features::shaderBufferInt64Atomics); + shaderSharedInt64Atomics = &(VkPhysicalDeviceShaderAtomicInt64Features::shaderSharedInt64Atomics); + shaderFloat16 = &(VkPhysicalDeviceShaderFloat16Int8Features::shaderFloat16); + shaderInt8 = &(VkPhysicalDeviceShaderFloat16Int8Features::shaderInt8); + shaderInputAttachmentArrayDynamicIndexing = &(VkPhysicalDeviceDescriptorIndexingFeatures::shaderInputAttachmentArrayDynamicIndexing); + shaderUniformTexelBufferArrayDynamicIndexing = &(VkPhysicalDeviceDescriptorIndexingFeatures::shaderUniformTexelBufferArrayDynamicIndexing); + shaderStorageTexelBufferArrayDynamicIndexing = &(VkPhysicalDeviceDescriptorIndexingFeatures::shaderStorageTexelBufferArrayDynamicIndexing); + shaderUniformBufferArrayNonUniformIndexing = &(VkPhysicalDeviceDescriptorIndexingFeatures::shaderUniformBufferArrayNonUniformIndexing); + shaderSampledImageArrayNonUniformIndexing = &(VkPhysicalDeviceDescriptorIndexingFeatures::shaderSampledImageArrayNonUniformIndexing); + shaderStorageBufferArrayNonUniformIndexing = &(VkPhysicalDeviceDescriptorIndexingFeatures::shaderStorageBufferArrayNonUniformIndexing); + shaderStorageImageArrayNonUniformIndexing = &(VkPhysicalDeviceDescriptorIndexingFeatures::shaderStorageImageArrayNonUniformIndexing); + shaderInputAttachmentArrayNonUniformIndexing = &(VkPhysicalDeviceDescriptorIndexingFeatures::shaderInputAttachmentArrayNonUniformIndexing); + shaderUniformTexelBufferArrayNonUniformIndexing = &(VkPhysicalDeviceDescriptorIndexingFeatures::shaderUniformTexelBufferArrayNonUniformIndexing); + shaderStorageTexelBufferArrayNonUniformIndexing = &(VkPhysicalDeviceDescriptorIndexingFeatures::shaderStorageTexelBufferArrayNonUniformIndexing); + descriptorBindingUniformBufferUpdateAfterBind = &(VkPhysicalDeviceDescriptorIndexingFeatures::descriptorBindingUniformBufferUpdateAfterBind); + descriptorBindingSampledImageUpdateAfterBind = &(VkPhysicalDeviceDescriptorIndexingFeatures::descriptorBindingSampledImageUpdateAfterBind); + descriptorBindingStorageImageUpdateAfterBind = &(VkPhysicalDeviceDescriptorIndexingFeatures::descriptorBindingStorageImageUpdateAfterBind); + descriptorBindingStorageBufferUpdateAfterBind = &(VkPhysicalDeviceDescriptorIndexingFeatures::descriptorBindingStorageBufferUpdateAfterBind); + descriptorBindingUniformTexelBufferUpdateAfterBind = &(VkPhysicalDeviceDescriptorIndexingFeatures::descriptorBindingUniformTexelBufferUpdateAfterBind); + descriptorBindingStorageTexelBufferUpdateAfterBind = &(VkPhysicalDeviceDescriptorIndexingFeatures::descriptorBindingStorageTexelBufferUpdateAfterBind); + descriptorBindingUpdateUnusedWhilePending = &(VkPhysicalDeviceDescriptorIndexingFeatures::descriptorBindingUpdateUnusedWhilePending); + descriptorBindingPartiallyBound = &(VkPhysicalDeviceDescriptorIndexingFeatures::descriptorBindingPartiallyBound); + descriptorBindingVariableDescriptorCount = &(VkPhysicalDeviceDescriptorIndexingFeatures::descriptorBindingVariableDescriptorCount); + runtimeDescriptorArray = &(VkPhysicalDeviceDescriptorIndexingFeatures::runtimeDescriptorArray); + scalarBlockLayout = &(VkPhysicalDeviceScalarBlockLayoutFeatures::scalarBlockLayout); + imagelessFramebuffer = &(VkPhysicalDeviceImagelessFramebufferFeatures::imagelessFramebuffer); + uniformBufferStandardLayout = &(VkPhysicalDeviceUniformBufferStandardLayoutFeatures::uniformBufferStandardLayout); + shaderSubgroupExtendedTypes = &(VkPhysicalDeviceShaderSubgroupExtendedTypesFeatures::shaderSubgroupExtendedTypes); + separateDepthStencilLayouts = &(VkPhysicalDeviceSeparateDepthStencilLayoutsFeatures::separateDepthStencilLayouts); + hostQueryReset = &(VkPhysicalDeviceHostQueryResetFeatures::hostQueryReset); + timelineSemaphore = &(VkPhysicalDeviceTimelineSemaphoreFeatures::timelineSemaphore); + bufferDeviceAddress = &(VkPhysicalDeviceBufferDeviceAddressFeatures::bufferDeviceAddress); + bufferDeviceAddressCaptureReplay = &(VkPhysicalDeviceBufferDeviceAddressFeatures::bufferDeviceAddressCaptureReplay); + bufferDeviceAddressMultiDevice = &(VkPhysicalDeviceBufferDeviceAddressFeatures::bufferDeviceAddressMultiDevice); + vulkanMemoryModel = &(VkPhysicalDeviceVulkanMemoryModelFeatures::vulkanMemoryModel); + vulkanMemoryModelDeviceScope = &(VkPhysicalDeviceVulkanMemoryModelFeatures::vulkanMemoryModelDeviceScope); + vulkanMemoryModelAvailabilityVisibilityChains = &(VkPhysicalDeviceVulkanMemoryModelFeatures::vulkanMemoryModelAvailabilityVisibilityChains); + + // These features are only available in 1.2 Core +// samplerMirrorClampToEdge = &(VkPhysicalDeviceVulkan12Features::samplerMirrorClampToEdge); +// drawIndirectCount = &(VkPhysicalDeviceVulkan12Features::drawIndirectCount); +// samplerFilterMinmax = &(VkPhysicalDeviceVulkan12Features::samplerFilterMinmax); +// shaderOutputViewportIndex = &(VkPhysicalDeviceVulkan12Features::shaderOutputViewportIndex); +// shaderOutputLayer = &(VkPhysicalDeviceVulkan12Features::shaderOutputLayer); +// subgroupBroadcastDynamicId = &(VkPhysicalDeviceVulkan12Features::subgroupBroadcastDynamicId); + + + // Daisy chain + VkPhysicalDevice8BitStorageFeatures::pNext = static_cast(this); + VkPhysicalDeviceShaderAtomicInt64Features::pNext = static_cast(this); + VkPhysicalDeviceShaderFloat16Int8Features::pNext = static_cast(this); + VkPhysicalDeviceDescriptorIndexingFeatures::pNext = static_cast(this); + VkPhysicalDeviceScalarBlockLayoutFeatures::pNext = static_cast(this); + VkPhysicalDeviceImagelessFramebufferFeatures::pNext = static_cast(this); + VkPhysicalDeviceUniformBufferStandardLayoutFeatures::pNext = static_cast(this); + VkPhysicalDeviceShaderSubgroupExtendedTypesFeatures::pNext = static_cast(this); + VkPhysicalDeviceSeparateDepthStencilLayoutsFeatures::pNext = static_cast(this); + VkPhysicalDeviceHostQueryResetFeatures::pNext = static_cast(this); + VkPhysicalDeviceTimelineSemaphoreFeatures::pNext = static_cast(this); + VkPhysicalDeviceBufferDeviceAddressFeatures::pNext = static_cast(this); + VkPhysicalDeviceVulkanMemoryModelFeatures::pNext = nullptr; + } +}; + +/// +/// \brief Core 1.3 Features +struct device_features_13 : private VkPhysicalDeviceVulkan13Features, + private VkPhysicalDeviceImageRobustnessFeatures, + private VkPhysicalDeviceInlineUniformBlockFeatures, + private VkPhysicalDevicePipelineCreationCacheControlFeatures, + private VkPhysicalDevicePrivateDataFeatures, + private VkPhysicalDeviceShaderDemoteToHelperInvocationFeatures, + private VkPhysicalDeviceShaderTerminateInvocationFeatures, + private VkPhysicalDeviceSubgroupSizeControlFeatures, + private VkPhysicalDeviceSynchronization2Features, + private VkPhysicalDeviceTextureCompressionASTCHDRFeatures, + private VkPhysicalDeviceZeroInitializeWorkgroupMemoryFeatures, + private VkPhysicalDeviceDynamicRenderingFeatures, + private VkPhysicalDeviceShaderIntegerDotProductFeatures, + private VkPhysicalDeviceMaintenance4Features { + +// Public References --------------------------------------------------------------------------------------------------- +public: + + /// \name Features + /// @{ + + VkBool32* robustImageAccess; //!< Robust Image Access + VkBool32* inlineUniformBlock; //!< Inline Uniform Block + VkBool32* descriptorBindingInlineUniformBlockUpdateAfterBind; //!< Descriptor Binding Inline Uniform Block Update After Bind + VkBool32* pipelineCreationCacheControl; //!< Pipeline Creation Cache Control + VkBool32* privateData; //!< Private Data + VkBool32* shaderDemoteToHelperInvocation; //!< Shader Demote To Helper Invocation + VkBool32* shaderTerminateInvocation; //!< Shader Terminate Invocation + VkBool32* subgroupSizeControl; //!< Subgroup Size Control + VkBool32* computeFullSubgroups; //!< Compute Full Subgroups + VkBool32* synchronization2; //!< Synchronization 2 + VkBool32* textureCompressionASTC_HDR; //!< Texture Compression Astc Hdr + VkBool32* shaderZeroInitializeWorkgroupMemory; //!< Shader Zero Initialize Workgroup Memory + VkBool32* dynamicRendering; //!< Dynamic Rendering + VkBool32* shaderIntegerDotProduct; //!< Shader Integer Dot Product + VkBool32* maintenance4; //!< Maintenance 4 + VkBool32 useCore; //!< Use Core + + /// @} + + +// Methods ------------------------------------------------------------------------------------------------------------- +public: + + /// + /// \brief Default Constructor + /// \details Version information is necessary for this structure to fill itself in properly, so the default + /// constructor is not allowed. + device_features_13() = delete; + + /// + /// \brief Features Constructor + /// \param properties Properties structure to poll necessary information + device_features_13(const device_properties& properties) + : VkPhysicalDeviceVulkan13Features { } + , VkPhysicalDeviceImageRobustnessFeatures { } + , VkPhysicalDeviceInlineUniformBlockFeatures { } + , VkPhysicalDevicePipelineCreationCacheControlFeatures { } + , VkPhysicalDevicePrivateDataFeatures { } + , VkPhysicalDeviceShaderDemoteToHelperInvocationFeatures { } + , VkPhysicalDeviceShaderTerminateInvocationFeatures { } + , VkPhysicalDeviceSubgroupSizeControlFeatures { } + , VkPhysicalDeviceSynchronization2Features { } + , VkPhysicalDeviceTextureCompressionASTCHDRFeatures { } + , VkPhysicalDeviceZeroInitializeWorkgroupMemoryFeatures { } + , VkPhysicalDeviceDynamicRenderingFeatures { } + , VkPhysicalDeviceShaderIntegerDotProductFeatures { } + , VkPhysicalDeviceMaintenance4Features { } + , robustImageAccess { nullptr } + , inlineUniformBlock { nullptr } + , descriptorBindingInlineUniformBlockUpdateAfterBind { nullptr } + , pipelineCreationCacheControl { nullptr } + , privateData { nullptr } + , shaderDemoteToHelperInvocation { nullptr } + , shaderTerminateInvocation { nullptr } + , subgroupSizeControl { nullptr } + , computeFullSubgroups { nullptr } + , synchronization2 { nullptr } + , textureCompressionASTC_HDR { nullptr } + , shaderZeroInitializeWorkgroupMemory { nullptr } + , dynamicRendering { nullptr } + , shaderIntegerDotProduct { nullptr } + , maintenance4 { nullptr } + , useCore { properties.core10->apiVersion >= VK_API_VERSION_1_3 } { + + _clear(); + _link(); + } + + /// + /// \brief Copy Constructor + /// \param features The features structure to copy + device_features_13(const device_features_13& features) + : VkPhysicalDeviceVulkan13Features { features } + , VkPhysicalDeviceImageRobustnessFeatures { features } + , VkPhysicalDeviceInlineUniformBlockFeatures { features } + , VkPhysicalDevicePipelineCreationCacheControlFeatures { features } + , VkPhysicalDevicePrivateDataFeatures { features } + , VkPhysicalDeviceShaderDemoteToHelperInvocationFeatures { features } + , VkPhysicalDeviceShaderTerminateInvocationFeatures { features } + , VkPhysicalDeviceSubgroupSizeControlFeatures { features } + , VkPhysicalDeviceSynchronization2Features { features } + , VkPhysicalDeviceTextureCompressionASTCHDRFeatures { features } + , VkPhysicalDeviceZeroInitializeWorkgroupMemoryFeatures { features } + , VkPhysicalDeviceDynamicRenderingFeatures { features } + , VkPhysicalDeviceShaderIntegerDotProductFeatures { features } + , VkPhysicalDeviceMaintenance4Features { features } + , robustImageAccess { nullptr } + , inlineUniformBlock { nullptr } + , descriptorBindingInlineUniformBlockUpdateAfterBind { nullptr } + , pipelineCreationCacheControl { nullptr } + , privateData { nullptr } + , shaderDemoteToHelperInvocation { nullptr } + , shaderTerminateInvocation { nullptr } + , subgroupSizeControl { nullptr } + , computeFullSubgroups { nullptr } + , synchronization2 { nullptr } + , textureCompressionASTC_HDR { nullptr } + , shaderZeroInitializeWorkgroupMemory { nullptr } + , dynamicRendering { nullptr } + , shaderIntegerDotProduct { nullptr } + , maintenance4 { nullptr } + , useCore { features.useCore } { + + _link(); + } + + /// + /// \brief Copy Constructor + /// \param features The features structure to copy + /// \returns A reference to \emph{self} + device_features_13& operator=(const device_features_13& features) { + if (this == &features) { + return *this; + } + + // Copy data + VkPhysicalDeviceVulkan13Features::operator=(features); + VkPhysicalDeviceImageRobustnessFeatures::operator=(features); + VkPhysicalDeviceInlineUniformBlockFeatures::operator=(features); + VkPhysicalDevicePipelineCreationCacheControlFeatures::operator=(features); + VkPhysicalDevicePrivateDataFeatures::operator=(features); + VkPhysicalDeviceShaderDemoteToHelperInvocationFeatures::operator=(features); + VkPhysicalDeviceShaderTerminateInvocationFeatures::operator=(features); + VkPhysicalDeviceSubgroupSizeControlFeatures::operator=(features); + VkPhysicalDeviceSynchronization2Features::operator=(features); + VkPhysicalDeviceTextureCompressionASTCHDRFeatures::operator=(features); + VkPhysicalDeviceZeroInitializeWorkgroupMemoryFeatures::operator=(features); + VkPhysicalDeviceDynamicRenderingFeatures::operator=(features); + VkPhysicalDeviceShaderIntegerDotProductFeatures::operator=(features); + VkPhysicalDeviceMaintenance4Features::operator=(features); + useCore = features.useCore; + + _link(); + + return *this; + } + + /// + /// \brief Chain an extension structure + /// \param next + void chain(void* next) { + if (useCore) { + VkPhysicalDeviceVulkan13Features::pNext = next; + } else { + VkPhysicalDeviceMaintenance4Features::pNext = next; + } + } + + /// + /// \brief Implicit casting for chaining + operator void*() { + if (useCore) { + return static_cast(this); + } else { + return static_cast(this); + } + } + + +// Helpers ------------------------------------------------------------------------------------------------------------- +private: + + void _clear() { + + // Clear out the struct + fennec::memset(this, 0, sizeof(*this)); + + // Set structure types + VkPhysicalDeviceVulkan13Features::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_VULKAN_1_3_FEATURES; + VkPhysicalDeviceImageRobustnessFeatures::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_IMAGE_ROBUSTNESS_FEATURES; + VkPhysicalDeviceInlineUniformBlockFeatures::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_INLINE_UNIFORM_BLOCK_FEATURES; + VkPhysicalDevicePipelineCreationCacheControlFeatures::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_PIPELINE_CREATION_CACHE_CONTROL_FEATURES; + VkPhysicalDevicePrivateDataFeatures::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_PRIVATE_DATA_FEATURES; + VkPhysicalDeviceShaderDemoteToHelperInvocationFeatures::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SHADER_DEMOTE_TO_HELPER_INVOCATION_FEATURES; + VkPhysicalDeviceShaderTerminateInvocationFeatures::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SHADER_TERMINATE_INVOCATION_FEATURES; + VkPhysicalDeviceSubgroupSizeControlFeatures::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SUBGROUP_SIZE_CONTROL_FEATURES; + VkPhysicalDeviceSynchronization2Features::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SYNCHRONIZATION_2_FEATURES; + VkPhysicalDeviceTextureCompressionASTCHDRFeatures::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_TEXTURE_COMPRESSION_ASTC_HDR_FEATURES; + VkPhysicalDeviceZeroInitializeWorkgroupMemoryFeatures::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_ZERO_INITIALIZE_WORKGROUP_MEMORY_FEATURES; + VkPhysicalDeviceDynamicRenderingFeatures::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_DYNAMIC_RENDERING_FEATURES; + VkPhysicalDeviceShaderIntegerDotProductFeatures::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SHADER_INTEGER_DOT_PRODUCT_FEATURES; + VkPhysicalDeviceMaintenance4Features::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_MAINTENANCE_4_FEATURES; + } + + void _link() { + + // Check if we are Version 1.3 or later. + if (useCore) { + + // Link to Core structure + robustImageAccess = &(VkPhysicalDeviceVulkan13Features::robustImageAccess); + inlineUniformBlock = &(VkPhysicalDeviceVulkan13Features::inlineUniformBlock); + descriptorBindingInlineUniformBlockUpdateAfterBind = &(VkPhysicalDeviceVulkan13Features::descriptorBindingInlineUniformBlockUpdateAfterBind); + pipelineCreationCacheControl = &(VkPhysicalDeviceVulkan13Features::pipelineCreationCacheControl); + privateData = &(VkPhysicalDeviceVulkan13Features::privateData); + shaderDemoteToHelperInvocation = &(VkPhysicalDeviceVulkan13Features::shaderDemoteToHelperInvocation); + shaderTerminateInvocation = &(VkPhysicalDeviceVulkan13Features::shaderTerminateInvocation); + subgroupSizeControl = &(VkPhysicalDeviceVulkan13Features::subgroupSizeControl); + computeFullSubgroups = &(VkPhysicalDeviceVulkan13Features::computeFullSubgroups); + synchronization2 = &(VkPhysicalDeviceVulkan13Features::synchronization2); + textureCompressionASTC_HDR = &(VkPhysicalDeviceVulkan13Features::textureCompressionASTC_HDR); + shaderZeroInitializeWorkgroupMemory = &(VkPhysicalDeviceVulkan13Features::shaderZeroInitializeWorkgroupMemory); + dynamicRendering = &(VkPhysicalDeviceVulkan13Features::dynamicRendering); + shaderIntegerDotProduct = &(VkPhysicalDeviceVulkan13Features::shaderIntegerDotProduct); + maintenance4 = &(VkPhysicalDeviceVulkan13Features::maintenance4); + + VkPhysicalDeviceVulkan13Features::pNext = nullptr; + + return; + } + + + // Link to Feature structures + robustImageAccess = &(VkPhysicalDeviceImageRobustnessFeatures::robustImageAccess); + inlineUniformBlock = &(VkPhysicalDeviceInlineUniformBlockFeatures::inlineUniformBlock); + descriptorBindingInlineUniformBlockUpdateAfterBind = &(VkPhysicalDeviceInlineUniformBlockFeatures::descriptorBindingInlineUniformBlockUpdateAfterBind); + pipelineCreationCacheControl = &(VkPhysicalDevicePipelineCreationCacheControlFeatures::pipelineCreationCacheControl); + privateData = &(VkPhysicalDevicePrivateDataFeatures::privateData); + shaderDemoteToHelperInvocation = &(VkPhysicalDeviceShaderDemoteToHelperInvocationFeatures::shaderDemoteToHelperInvocation); + shaderTerminateInvocation = &(VkPhysicalDeviceShaderTerminateInvocationFeatures::shaderTerminateInvocation); + subgroupSizeControl = &(VkPhysicalDeviceSubgroupSizeControlFeatures::subgroupSizeControl); + computeFullSubgroups = &(VkPhysicalDeviceSubgroupSizeControlFeatures::computeFullSubgroups); + synchronization2 = &(VkPhysicalDeviceSynchronization2Features::synchronization2); + textureCompressionASTC_HDR = &(VkPhysicalDeviceTextureCompressionASTCHDRFeatures::textureCompressionASTC_HDR); + shaderZeroInitializeWorkgroupMemory = &(VkPhysicalDeviceZeroInitializeWorkgroupMemoryFeatures::shaderZeroInitializeWorkgroupMemory); + dynamicRendering = &(VkPhysicalDeviceDynamicRenderingFeatures::dynamicRendering); + shaderIntegerDotProduct = &(VkPhysicalDeviceShaderIntegerDotProductFeatures::shaderIntegerDotProduct); + maintenance4 = &(VkPhysicalDeviceMaintenance4Features::maintenance4); + + + // Daisy Chain + VkPhysicalDeviceVulkan13Features::pNext = static_cast(this); + VkPhysicalDeviceImageRobustnessFeatures::pNext = static_cast(this); + VkPhysicalDeviceInlineUniformBlockFeatures::pNext = static_cast(this); + VkPhysicalDevicePipelineCreationCacheControlFeatures::pNext = static_cast(this); + VkPhysicalDevicePrivateDataFeatures::pNext = static_cast(this); + VkPhysicalDeviceShaderDemoteToHelperInvocationFeatures::pNext = static_cast(this); + VkPhysicalDeviceShaderTerminateInvocationFeatures::pNext = static_cast(this); + VkPhysicalDeviceSubgroupSizeControlFeatures::pNext = static_cast(this); + VkPhysicalDeviceSynchronization2Features::pNext = static_cast(this); + VkPhysicalDeviceTextureCompressionASTCHDRFeatures::pNext = static_cast(this); + VkPhysicalDeviceZeroInitializeWorkgroupMemoryFeatures::pNext = static_cast(this); + VkPhysicalDeviceDynamicRenderingFeatures::pNext = static_cast(this); + VkPhysicalDeviceShaderIntegerDotProductFeatures::pNext = static_cast(this); + VkPhysicalDeviceMaintenance4Features::pNext = nullptr; + } +}; + +/// +/// \brief Core 1.4 Features +struct device_features_14 : private VkPhysicalDeviceVulkan14Features, + private VkPhysicalDeviceGlobalPriorityQueryFeatures, + private VkPhysicalDeviceShaderSubgroupRotateFeatures, + private VkPhysicalDeviceShaderFloatControls2Features, + private VkPhysicalDeviceShaderExpectAssumeFeatures, + private VkPhysicalDeviceLineRasterizationFeatures, + private VkPhysicalDeviceVertexAttributeDivisorFeatures, + private VkPhysicalDeviceIndexTypeUint8Features, + private VkPhysicalDeviceDynamicRenderingLocalReadFeatures, + private VkPhysicalDeviceMaintenance5Features, + private VkPhysicalDeviceMaintenance6Features, + private VkPhysicalDevicePipelineProtectedAccessFeatures, + private VkPhysicalDevicePipelineRobustnessFeatures, + private VkPhysicalDeviceHostImageCopyFeatures { + +// Public References --------------------------------------------------------------------------------------------------- +public: + + /// \name Features + /// @{ + + VkBool32* globalPriorityQuery; //!< Global Priority Query + VkBool32* shaderSubgroupRotate; //!< Shader Subgroup Rotate + VkBool32* shaderSubgroupRotateClustered; //!< Shader Subgroup Rotate Clustered + VkBool32* shaderFloatControls2; //!< Shader Float Controls 2 + VkBool32* shaderExpectAssume; //!< Shader Expect Assume + VkBool32* rectangularLines; //!< Rectangular Lines + VkBool32* bresenhamLines; //!< Bresenham Lines + VkBool32* smoothLines; //!< Smooth Lines + VkBool32* stippledRectangularLines; //!< Stippled Rectangular Lines + VkBool32* stippledBresenhamLines; //!< Stippled Bresenham Lines + VkBool32* stippledSmoothLines; //!< Stippled Smooth Lines + VkBool32* vertexAttributeInstanceRateDivisor; //!< Vertex Attribute Instance Rate Divisor + VkBool32* vertexAttributeInstanceRateZeroDivisor; //!< Vertex Attribute Instance Rate Zero Divisor + VkBool32* indexTypeUint8; //!< Index Type Uint8 + VkBool32* dynamicRenderingLocalRead; //!< Dynamic Rendering Local Read + VkBool32* maintenance5; //!< Maintenance 5 + VkBool32* maintenance6; //!< Maintenance 6 + VkBool32* pipelineProtectedAccess; //!< Pipeline Protected Access + VkBool32* pipelineRobustness; //!< Pipeline Robustness + VkBool32* hostImageCopy; //!< Host Image Copy + VkBool32* pushDescriptor; //!< Push Descriptor + VkBool32 useCore; //!< Use Core + + /// @} + + +// Methods ------------------------------------------------------------------------------------------------------------- +public: + + /// + /// \brief Default Constructor + /// \details Version information is necessary for this structure to fill itself in properly, so the default + /// constructor is not allowed. + device_features_14() = delete; + + /// + /// \brief Features Constructor + /// \param properties Properties structure to poll necessary information + device_features_14(const device_properties& properties) + : VkPhysicalDeviceVulkan14Features { } + , VkPhysicalDeviceGlobalPriorityQueryFeatures { } + , VkPhysicalDeviceShaderSubgroupRotateFeatures { } + , VkPhysicalDeviceShaderFloatControls2Features { } + , VkPhysicalDeviceShaderExpectAssumeFeatures { } + , VkPhysicalDeviceLineRasterizationFeatures { } + , VkPhysicalDeviceVertexAttributeDivisorFeatures { } + , VkPhysicalDeviceIndexTypeUint8Features { } + , VkPhysicalDeviceDynamicRenderingLocalReadFeatures { } + , VkPhysicalDeviceMaintenance5Features { } + , VkPhysicalDeviceMaintenance6Features { } + , VkPhysicalDevicePipelineProtectedAccessFeatures { } + , VkPhysicalDevicePipelineRobustnessFeatures { } + , VkPhysicalDeviceHostImageCopyFeatures { } + , globalPriorityQuery { nullptr } + , shaderSubgroupRotate { nullptr } + , shaderSubgroupRotateClustered { nullptr } + , shaderFloatControls2 { nullptr } + , shaderExpectAssume { nullptr } + , rectangularLines { nullptr } + , bresenhamLines { nullptr } + , smoothLines { nullptr } + , stippledRectangularLines { nullptr } + , stippledBresenhamLines { nullptr } + , stippledSmoothLines { nullptr } + , vertexAttributeInstanceRateDivisor { nullptr } + , vertexAttributeInstanceRateZeroDivisor { nullptr } + , indexTypeUint8 { nullptr } + , dynamicRenderingLocalRead { nullptr } + , maintenance5 { nullptr } + , maintenance6 { nullptr } + , pipelineProtectedAccess { nullptr } + , pipelineRobustness { nullptr } + , hostImageCopy { nullptr } + , pushDescriptor { nullptr } + , useCore { properties.core10->apiVersion >= VK_API_VERSION_1_4 } { + + _link(); + } + + /// + /// \brief Copy Constructor + /// \param features The features structure to copy + device_features_14(const device_features_14& features) + : VkPhysicalDeviceVulkan14Features { features } + , VkPhysicalDeviceGlobalPriorityQueryFeatures { features } + , VkPhysicalDeviceShaderSubgroupRotateFeatures { features } + , VkPhysicalDeviceShaderFloatControls2Features { features } + , VkPhysicalDeviceShaderExpectAssumeFeatures { features } + , VkPhysicalDeviceLineRasterizationFeatures { features } + , VkPhysicalDeviceVertexAttributeDivisorFeatures { features } + , VkPhysicalDeviceIndexTypeUint8Features { features } + , VkPhysicalDeviceDynamicRenderingLocalReadFeatures { features } + , VkPhysicalDeviceMaintenance5Features { features } + , VkPhysicalDeviceMaintenance6Features { features } + , VkPhysicalDevicePipelineProtectedAccessFeatures { features } + , VkPhysicalDevicePipelineRobustnessFeatures { features } + , VkPhysicalDeviceHostImageCopyFeatures { features } + , globalPriorityQuery { nullptr } + , shaderSubgroupRotate { nullptr } + , shaderSubgroupRotateClustered { nullptr } + , shaderFloatControls2 { nullptr } + , shaderExpectAssume { nullptr } + , rectangularLines { nullptr } + , bresenhamLines { nullptr } + , smoothLines { nullptr } + , stippledRectangularLines { nullptr } + , stippledBresenhamLines { nullptr } + , stippledSmoothLines { nullptr } + , vertexAttributeInstanceRateDivisor { nullptr } + , vertexAttributeInstanceRateZeroDivisor { nullptr } + , indexTypeUint8 { nullptr } + , dynamicRenderingLocalRead { nullptr } + , maintenance5 { nullptr } + , maintenance6 { nullptr } + , pipelineProtectedAccess { nullptr } + , pipelineRobustness { nullptr } + , hostImageCopy { nullptr } + , pushDescriptor { nullptr } { + + _link(); + } + + /// + /// \brief Copy Assignment + /// \param features The features to copy + /// \returns A reference to \emph{this} + device_features_14& operator=(const device_features_14& features) { + if (this == &features) { + return *this; + } + + // Copy data + VkPhysicalDeviceVulkan14Features::operator=(features); + VkPhysicalDeviceGlobalPriorityQueryFeatures::operator=(features); + VkPhysicalDeviceShaderSubgroupRotateFeatures::operator=(features); + VkPhysicalDeviceShaderFloatControls2Features::operator=(features); + VkPhysicalDeviceShaderExpectAssumeFeatures::operator=(features); + VkPhysicalDeviceLineRasterizationFeatures::operator=(features); + VkPhysicalDeviceVertexAttributeDivisorFeatures::operator=(features); + VkPhysicalDeviceIndexTypeUint8Features::operator=(features); + VkPhysicalDeviceDynamicRenderingLocalReadFeatures::operator=(features); + VkPhysicalDeviceMaintenance5Features::operator=(features); + VkPhysicalDeviceMaintenance6Features::operator=(features); + VkPhysicalDevicePipelineProtectedAccessFeatures::operator=(features); + VkPhysicalDevicePipelineRobustnessFeatures::operator=(features); + VkPhysicalDeviceHostImageCopyFeatures::operator=(features); + useCore = features.useCore; + + _link(); + + return *this; + } + + /// + /// \brief Chain an extension structure + /// \param next + void chain(void* next) { + if (useCore) { + VkPhysicalDeviceVulkan14Features::pNext = next; + } else { + VkPhysicalDeviceHostImageCopyFeatures::pNext = next; + } + } + + /// + /// \brief Implicit casting for chaining + operator void*() { + if (useCore) { + return static_cast(this); + } else { + return static_cast(this); + } + } + + +// Helpers ------------------------------------------------------------------------------------------------------------- +private: + + void _clear() { + + // Clear out the struct + fennec::memset(this, 0, sizeof(*this)); + + + // Set the structure types + VkPhysicalDeviceVulkan14Features::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_VULKAN_1_4_FEATURES; + VkPhysicalDeviceGlobalPriorityQueryFeatures::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_GLOBAL_PRIORITY_QUERY_FEATURES; + VkPhysicalDeviceShaderSubgroupRotateFeatures::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SHADER_SUBGROUP_ROTATE_FEATURES; + VkPhysicalDeviceShaderFloatControls2Features::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SHADER_FLOAT_CONTROLS_2_FEATURES; + VkPhysicalDeviceShaderExpectAssumeFeatures::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SHADER_EXPECT_ASSUME_FEATURES; + VkPhysicalDeviceLineRasterizationFeatures::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_LINE_RASTERIZATION_FEATURES; + VkPhysicalDeviceVertexAttributeDivisorFeatures::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_VERTEX_ATTRIBUTE_DIVISOR_FEATURES; + VkPhysicalDeviceIndexTypeUint8Features::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_INDEX_TYPE_UINT8_FEATURES; + VkPhysicalDeviceDynamicRenderingLocalReadFeatures::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_DYNAMIC_RENDERING_LOCAL_READ_FEATURES; + VkPhysicalDeviceMaintenance5Features::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_MAINTENANCE_5_FEATURES; + VkPhysicalDeviceMaintenance6Features::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_MAINTENANCE_6_FEATURES; + VkPhysicalDevicePipelineProtectedAccessFeatures::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_PIPELINE_PROTECTED_ACCESS_FEATURES; + VkPhysicalDevicePipelineRobustnessFeatures::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_PIPELINE_ROBUSTNESS_FEATURES; + VkPhysicalDeviceHostImageCopyFeatures::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_HOST_IMAGE_COPY_FEATURES; + } + + void _link() { + + // Check if we are Version 1.4 or later. + if (useCore) { + + // Link to Core structure + globalPriorityQuery = &(VkPhysicalDeviceVulkan14Features::globalPriorityQuery); + shaderSubgroupRotate = &(VkPhysicalDeviceVulkan14Features::shaderSubgroupRotate); + shaderSubgroupRotateClustered = &(VkPhysicalDeviceVulkan14Features::shaderSubgroupRotateClustered); + shaderFloatControls2 = &(VkPhysicalDeviceVulkan14Features::shaderFloatControls2); + shaderExpectAssume = &(VkPhysicalDeviceVulkan14Features::shaderExpectAssume); + rectangularLines = &(VkPhysicalDeviceVulkan14Features::rectangularLines); + bresenhamLines = &(VkPhysicalDeviceVulkan14Features::bresenhamLines); + smoothLines = &(VkPhysicalDeviceVulkan14Features::smoothLines); + stippledRectangularLines = &(VkPhysicalDeviceVulkan14Features::stippledRectangularLines); + stippledBresenhamLines = &(VkPhysicalDeviceVulkan14Features::stippledBresenhamLines); + stippledSmoothLines = &(VkPhysicalDeviceVulkan14Features::stippledSmoothLines); + vertexAttributeInstanceRateDivisor = &(VkPhysicalDeviceVulkan14Features::vertexAttributeInstanceRateDivisor); + vertexAttributeInstanceRateZeroDivisor = &(VkPhysicalDeviceVulkan14Features::vertexAttributeInstanceRateZeroDivisor); + indexTypeUint8 = &(VkPhysicalDeviceVulkan14Features::indexTypeUint8); + dynamicRenderingLocalRead = &(VkPhysicalDeviceVulkan14Features::dynamicRenderingLocalRead); + maintenance5 = &(VkPhysicalDeviceVulkan14Features::maintenance5); + maintenance6 = &(VkPhysicalDeviceVulkan14Features::maintenance6); + pipelineProtectedAccess = &(VkPhysicalDeviceVulkan14Features::pipelineProtectedAccess); + pipelineRobustness = &(VkPhysicalDeviceVulkan14Features::pipelineRobustness); + hostImageCopy = &(VkPhysicalDeviceVulkan14Features::hostImageCopy); + pushDescriptor = &(VkPhysicalDeviceVulkan14Features::pushDescriptor); + + VkPhysicalDeviceVulkan14Features::pNext = nullptr; + + return; + } + + + // Link to Feature structures + globalPriorityQuery = &(VkPhysicalDeviceGlobalPriorityQueryFeatures::globalPriorityQuery); + shaderSubgroupRotate = &(VkPhysicalDeviceShaderSubgroupRotateFeatures::shaderSubgroupRotate); + shaderSubgroupRotateClustered = &(VkPhysicalDeviceShaderSubgroupRotateFeatures::shaderSubgroupRotateClustered); + shaderFloatControls2 = &(VkPhysicalDeviceShaderFloatControls2Features::shaderFloatControls2); + shaderExpectAssume = &(VkPhysicalDeviceShaderExpectAssumeFeatures::shaderExpectAssume); + rectangularLines = &(VkPhysicalDeviceLineRasterizationFeatures::rectangularLines); + bresenhamLines = &(VkPhysicalDeviceLineRasterizationFeatures::bresenhamLines); + smoothLines = &(VkPhysicalDeviceLineRasterizationFeatures::smoothLines); + stippledRectangularLines = &(VkPhysicalDeviceLineRasterizationFeatures::stippledRectangularLines); + stippledBresenhamLines = &(VkPhysicalDeviceLineRasterizationFeatures::stippledBresenhamLines); + stippledSmoothLines = &(VkPhysicalDeviceLineRasterizationFeatures::stippledSmoothLines); + vertexAttributeInstanceRateDivisor = &(VkPhysicalDeviceVertexAttributeDivisorFeatures::vertexAttributeInstanceRateDivisor); + vertexAttributeInstanceRateZeroDivisor = &(VkPhysicalDeviceVertexAttributeDivisorFeatures::vertexAttributeInstanceRateZeroDivisor); + indexTypeUint8 = &(VkPhysicalDeviceIndexTypeUint8Features::indexTypeUint8); + dynamicRenderingLocalRead = &(VkPhysicalDeviceDynamicRenderingLocalReadFeatures::dynamicRenderingLocalRead); + maintenance5 = &(VkPhysicalDeviceMaintenance5Features::maintenance5); + maintenance6 = &(VkPhysicalDeviceMaintenance6Features::maintenance6); + pipelineProtectedAccess = &(VkPhysicalDevicePipelineProtectedAccessFeatures::pipelineProtectedAccess); + pipelineRobustness = &(VkPhysicalDevicePipelineRobustnessFeatures::pipelineRobustness); + hostImageCopy = &(VkPhysicalDeviceHostImageCopyFeatures::hostImageCopy); + + // These features are only available in 1.4 Core +// pushDescriptor = &(VkPhysicalDeviceVulkan14Features::pushDescriptor); + + + // Daisy chain + VkPhysicalDeviceGlobalPriorityQueryFeatures::pNext = static_cast(this); + VkPhysicalDeviceShaderSubgroupRotateFeatures::pNext = static_cast(this); + VkPhysicalDeviceShaderFloatControls2Features::pNext = static_cast(this); + VkPhysicalDeviceShaderExpectAssumeFeatures::pNext = static_cast(this); + VkPhysicalDeviceLineRasterizationFeatures::pNext = static_cast(this); + VkPhysicalDeviceVertexAttributeDivisorFeatures::pNext = static_cast(this); + VkPhysicalDeviceIndexTypeUint8Features::pNext = static_cast(this); + VkPhysicalDeviceDynamicRenderingLocalReadFeatures::pNext = static_cast(this); + VkPhysicalDeviceMaintenance5Features::pNext = static_cast(this); + VkPhysicalDeviceMaintenance6Features::pNext = static_cast(this); + VkPhysicalDevicePipelineProtectedAccessFeatures::pNext = static_cast(this); + VkPhysicalDevicePipelineRobustnessFeatures::pNext = static_cast(this); + VkPhysicalDeviceHostImageCopyFeatures::pNext = nullptr; + } +}; + +/// +/// \brief KHR Features +struct device_features_khr : private VkPhysicalDeviceAccelerationStructureFeaturesKHR, + private VkPhysicalDeviceComputeShaderDerivativesFeaturesKHR, + private VkPhysicalDeviceCooperativeMatrixFeaturesKHR, + private VkPhysicalDeviceDepthClampZeroOneFeaturesKHR, + private VkPhysicalDeviceFragmentShaderBarycentricFeaturesKHR, + private VkPhysicalDeviceFragmentShadingRateFeaturesKHR, + private VkPhysicalDeviceMaintenance7FeaturesKHR, + private VkPhysicalDeviceMaintenance8FeaturesKHR, + private VkPhysicalDeviceMaintenance9FeaturesKHR, + private VkPhysicalDevicePerformanceQueryFeaturesKHR, + private VkPhysicalDevicePipelineBinaryFeaturesKHR, + private VkPhysicalDevicePipelineExecutablePropertiesFeaturesKHR, + private VkPhysicalDevicePresentIdFeaturesKHR, + private VkPhysicalDevicePresentId2FeaturesKHR, + private VkPhysicalDevicePresentModeFifoLatestReadyFeaturesKHR, + private VkPhysicalDevicePresentWaitFeaturesKHR, + private VkPhysicalDevicePresentWait2FeaturesKHR, + private VkPhysicalDeviceRayQueryFeaturesKHR, + private VkPhysicalDeviceRayTracingMaintenance1FeaturesKHR, + private VkPhysicalDeviceRayTracingPipelineFeaturesKHR, + private VkPhysicalDeviceRayTracingPositionFetchFeaturesKHR, + private VkPhysicalDeviceRobustness2FeaturesKHR, + private VkPhysicalDeviceShaderBfloat16FeaturesKHR, + private VkPhysicalDeviceShaderClockFeaturesKHR, + private VkPhysicalDeviceShaderMaximalReconvergenceFeaturesKHR, + private VkPhysicalDeviceShaderQuadControlFeaturesKHR, + private VkPhysicalDeviceShaderRelaxedExtendedInstructionFeaturesKHR, + private VkPhysicalDeviceShaderSubgroupUniformControlFlowFeaturesKHR, + private VkPhysicalDeviceSwapchainMaintenance1FeaturesKHR, + private VkPhysicalDeviceUnifiedImageLayoutsFeaturesKHR, + private VkPhysicalDeviceVideoDecodeVP9FeaturesKHR, + private VkPhysicalDeviceVideoEncodeAV1FeaturesKHR, + private VkPhysicalDeviceVideoEncodeIntraRefreshFeaturesKHR, + private VkPhysicalDeviceVideoEncodeQuantizationMapFeaturesKHR, + private VkPhysicalDeviceVideoMaintenance1FeaturesKHR, + private VkPhysicalDeviceVideoMaintenance2FeaturesKHR, + private VkPhysicalDeviceWorkgroupMemoryExplicitLayoutFeaturesKHR { + +// Public References --------------------------------------------------------------------------------------------------- +public: + + /// \name Features + /// @{ + + VkBool32* accelerationStructure; //!< Acceleration Structure + VkBool32* accelerationStructureCaptureReplay; //!< Acceleration Structure Capture Replay + VkBool32* accelerationStructureIndirectBuild; //!< Acceleration Structure Indirect Build + VkBool32* accelerationStructureHostCommands; //!< Acceleration Structure Host Commands + VkBool32* descriptorBindingAccelerationStructureUpdateAfterBind; //!< Descriptor Binding Acceleration Structure Update After Bind + VkBool32* computeDerivativeGroupQuads; //!< Compute Derivative Group Quads + VkBool32* computeDerivativeGroupLinear; //!< Compute Derivative Group Linear + VkBool32* cooperativeMatrix; //!< Cooperative Matrix + VkBool32* cooperativeMatrixRobustBufferAccess; //!< Cooperative Matrix Robust Buffer Access + VkBool32* depthClampZeroOne; //!< Depth Clamp Zero One + VkBool32* fragmentShaderBarycentric; //!< Fragment Shader Barycentric + VkBool32* pipelineFragmentShadingRate; //!< Pipeline Fragment Shading Rate + VkBool32* primitiveFragmentShadingRate; //!< Primitive Fragment Shading Rate + VkBool32* attachmentFragmentShadingRate; //!< Attachment Fragment Shading Rate + VkBool32* maintenance7; //!< Maintenance7 + VkBool32* maintenance8; //!< Maintenance8 + VkBool32* maintenance9; //!< Maintenance9 + VkBool32* performanceCounterQueryPools; //!< Performance Counter Query Pools + VkBool32* performanceCounterMultipleQueryPools; //!< Performance Counter Multiple Query Pools + VkBool32* pipelineBinaries; //!< Pipeline Binaries + VkBool32* pipelineExecutableInfo; //!< Pipeline Executable Info + VkBool32* presentId; //!< Present Id + VkBool32* presentId2; //!< Present Id 2 + VkBool32* presentModeFifoLatestReady; //!< Present Mode Fifo Latest Ready + VkBool32* presentWait; //!< Present Wait + VkBool32* presentWait2; //!< Present Wait 2 + VkBool32* rayQuery; //!< Ray Query + VkBool32* rayTracingMaintenance1; //!< Ray Tracing Maintenance1 + VkBool32* rayTracingPipelineTraceRaysIndirect2; //!< Ray Tracing Pipeline Trace Rays Indirect2 + VkBool32* rayTracingPipeline; //!< Ray Tracing Pipeline + VkBool32* rayTracingPipelineShaderGroupHandleCaptureReplay; //!< Ray Tracing Pipeline Shader Group Handle Capture Replay + VkBool32* rayTracingPipelineShaderGroupHandleCaptureReplayMixed; //!< Ray Tracing Pipeline Shader Group Handle Capture Replay Mixed + VkBool32* rayTracingPipelineTraceRaysIndirect; //!< Ray Tracing Pipeline Trace Rays Indirect + VkBool32* rayTraversalPrimitiveCulling; //!< Ray Traversal Primitive Culling + VkBool32* rayTracingPositionFetch; //!< Ray Tracing Position Fetch + VkBool32* robustBufferAccess2; //!< Robust Buffer Access 2 + VkBool32* robustImageAccess2; //!< Robust Image Access 2 + VkBool32* nullDescriptor; //!< Null Descriptor + VkBool32* shaderBFloat16Type; //!< Shader B Float16 Type + VkBool32* shaderBFloat16DotProduct; //!< Shader B Float16 Dot Product + VkBool32* shaderBFloat16CooperativeMatrix; //!< Shader B Float16 Cooperative Matrix + VkBool32* shaderSubgroupClock; //!< Shader Subgroup Clock + VkBool32* shaderDeviceClock; //!< Shader Device Clock + VkBool32* shaderMaximalReconvergence; //!< Shader Maximal Reconvergence + VkBool32* shaderQuadControl; //!< Shader Quad Control + VkBool32* shaderRelaxedExtendedInstruction; //!< Shader Relaxed Extended Instruction + VkBool32* shaderSubgroupUniformControlFlow; //!< Shader Subgroup Uniform Control Flow + VkBool32* swapchainMaintenance1; //!< Swapchain Maintenance 1 + VkBool32* unifiedImageLayouts; //!< Unified Image Layouts + VkBool32* unifiedImageLayoutsVideo; //!< Unified Image Layouts Video + VkBool32* videoDecodeVP9; //!< Video Decode Vp9 + VkBool32* videoEncodeAV1; //!< Video Encode Av1 + VkBool32* videoEncodeIntraRefresh; //!< Video Encode Intra Refresh + VkBool32* videoEncodeQuantizationMap; //!< Video Encode Quantization Map + VkBool32* videoMaintenance1; //!< Video Maintenance1 + VkBool32* videoMaintenance2; //!< Video Maintenance2 + VkBool32* workgroupMemoryExplicitLayout; //!< Workgroup Memory Explicit Layout + VkBool32* workgroupMemoryExplicitLayoutScalarBlockLayout; //!< Workgroup Memory Explicit Layout Scalar Block Layout + VkBool32* workgroupMemoryExplicitLayout8BitAccess; //!< Workgroup Memory Explicit Layout 8-Bit Access + VkBool32* workgroupMemoryExplicitLayout16BitAccess; //!< Workgroup Memory Explicit Layout 16-Bit Access + + /// @} + + +// Methods ------------------------------------------------------------------------------------------------------------- +public: + + /// + /// \brief Features Constructor + device_features_khr() + : VkPhysicalDeviceAccelerationStructureFeaturesKHR { } + , VkPhysicalDeviceComputeShaderDerivativesFeaturesKHR { } + , VkPhysicalDeviceCooperativeMatrixFeaturesKHR { } + , VkPhysicalDeviceDepthClampZeroOneFeaturesKHR { } + , VkPhysicalDeviceFragmentShaderBarycentricFeaturesKHR { } + , VkPhysicalDeviceFragmentShadingRateFeaturesKHR { } + , VkPhysicalDeviceMaintenance7FeaturesKHR { } + , VkPhysicalDeviceMaintenance8FeaturesKHR { } + , VkPhysicalDeviceMaintenance9FeaturesKHR { } + , VkPhysicalDevicePerformanceQueryFeaturesKHR { } + , VkPhysicalDevicePipelineBinaryFeaturesKHR { } + , VkPhysicalDevicePipelineExecutablePropertiesFeaturesKHR { } + , VkPhysicalDevicePresentIdFeaturesKHR { } + , VkPhysicalDevicePresentId2FeaturesKHR { } + , VkPhysicalDevicePresentModeFifoLatestReadyFeaturesKHR { } + , VkPhysicalDevicePresentWaitFeaturesKHR { } + , VkPhysicalDevicePresentWait2FeaturesKHR { } + , VkPhysicalDeviceRayQueryFeaturesKHR { } + , VkPhysicalDeviceRayTracingMaintenance1FeaturesKHR { } + , VkPhysicalDeviceRayTracingPipelineFeaturesKHR { } + , VkPhysicalDeviceRayTracingPositionFetchFeaturesKHR { } + , VkPhysicalDeviceRobustness2FeaturesKHR { } + , VkPhysicalDeviceShaderBfloat16FeaturesKHR { } + , VkPhysicalDeviceShaderClockFeaturesKHR { } + , VkPhysicalDeviceShaderMaximalReconvergenceFeaturesKHR { } + , VkPhysicalDeviceShaderQuadControlFeaturesKHR { } + , VkPhysicalDeviceShaderRelaxedExtendedInstructionFeaturesKHR { } + , VkPhysicalDeviceShaderSubgroupUniformControlFlowFeaturesKHR { } + , VkPhysicalDeviceSwapchainMaintenance1FeaturesKHR { } + , VkPhysicalDeviceUnifiedImageLayoutsFeaturesKHR { } + , VkPhysicalDeviceVideoDecodeVP9FeaturesKHR { } + , VkPhysicalDeviceVideoEncodeAV1FeaturesKHR { } + , VkPhysicalDeviceVideoEncodeIntraRefreshFeaturesKHR { } + , VkPhysicalDeviceVideoEncodeQuantizationMapFeaturesKHR { } + , VkPhysicalDeviceVideoMaintenance1FeaturesKHR { } + , VkPhysicalDeviceVideoMaintenance2FeaturesKHR { } + , VkPhysicalDeviceWorkgroupMemoryExplicitLayoutFeaturesKHR { } + , accelerationStructure { nullptr } + , accelerationStructureCaptureReplay { nullptr } + , accelerationStructureIndirectBuild { nullptr } + , accelerationStructureHostCommands { nullptr } + , descriptorBindingAccelerationStructureUpdateAfterBind { nullptr } + , computeDerivativeGroupQuads { nullptr } + , computeDerivativeGroupLinear { nullptr } + , cooperativeMatrix { nullptr } + , cooperativeMatrixRobustBufferAccess { nullptr } + , depthClampZeroOne { nullptr } + , fragmentShaderBarycentric { nullptr } + , pipelineFragmentShadingRate { nullptr } + , primitiveFragmentShadingRate { nullptr } + , attachmentFragmentShadingRate { nullptr } + , maintenance7 { nullptr } + , maintenance8 { nullptr } + , maintenance9 { nullptr } + , performanceCounterQueryPools { nullptr } + , performanceCounterMultipleQueryPools { nullptr } + , pipelineBinaries { nullptr } + , pipelineExecutableInfo { nullptr } + , presentId { nullptr } + , presentId2 { nullptr } + , presentModeFifoLatestReady { nullptr } + , presentWait { nullptr } + , presentWait2 { nullptr } + , rayQuery { nullptr } + , rayTracingMaintenance1 { nullptr } + , rayTracingPipelineTraceRaysIndirect2 { nullptr } + , rayTracingPipeline { nullptr } + , rayTracingPipelineShaderGroupHandleCaptureReplay { nullptr } + , rayTracingPipelineShaderGroupHandleCaptureReplayMixed { nullptr } + , rayTracingPipelineTraceRaysIndirect { nullptr } + , rayTraversalPrimitiveCulling { nullptr } + , rayTracingPositionFetch { nullptr } + , robustBufferAccess2 { nullptr } + , robustImageAccess2 { nullptr } + , nullDescriptor { nullptr } + , shaderBFloat16Type { nullptr } + , shaderBFloat16DotProduct { nullptr } + , shaderBFloat16CooperativeMatrix { nullptr } + , shaderSubgroupClock { nullptr } + , shaderDeviceClock { nullptr } + , shaderMaximalReconvergence { nullptr } + , shaderQuadControl { nullptr } + , shaderRelaxedExtendedInstruction { nullptr } + , shaderSubgroupUniformControlFlow { nullptr } + , swapchainMaintenance1 { nullptr } + , unifiedImageLayouts { nullptr } + , unifiedImageLayoutsVideo { nullptr } + , videoDecodeVP9 { nullptr } + , videoEncodeAV1 { nullptr } + , videoEncodeIntraRefresh { nullptr } + , videoEncodeQuantizationMap { nullptr } + , videoMaintenance1 { nullptr } + , videoMaintenance2 { nullptr } + , workgroupMemoryExplicitLayout { nullptr } + , workgroupMemoryExplicitLayoutScalarBlockLayout { nullptr } + , workgroupMemoryExplicitLayout8BitAccess { nullptr } + , workgroupMemoryExplicitLayout16BitAccess { nullptr } { + + _link(); + } + + /// + /// \brief Copy Constructor + /// \param features The features structure to copy + device_features_khr(const device_features_khr& features) + : VkPhysicalDeviceAccelerationStructureFeaturesKHR { features } + , VkPhysicalDeviceComputeShaderDerivativesFeaturesKHR { features } + , VkPhysicalDeviceCooperativeMatrixFeaturesKHR { features } + , VkPhysicalDeviceDepthClampZeroOneFeaturesKHR { features } + , VkPhysicalDeviceFragmentShaderBarycentricFeaturesKHR { features } + , VkPhysicalDeviceFragmentShadingRateFeaturesKHR { features } + , VkPhysicalDeviceMaintenance7FeaturesKHR { features } + , VkPhysicalDeviceMaintenance8FeaturesKHR { features } + , VkPhysicalDeviceMaintenance9FeaturesKHR { features } + , VkPhysicalDevicePerformanceQueryFeaturesKHR { features } + , VkPhysicalDevicePipelineBinaryFeaturesKHR { features } + , VkPhysicalDevicePipelineExecutablePropertiesFeaturesKHR { features } + , VkPhysicalDevicePresentIdFeaturesKHR { features } + , VkPhysicalDevicePresentId2FeaturesKHR { features } + , VkPhysicalDevicePresentModeFifoLatestReadyFeaturesKHR { features } + , VkPhysicalDevicePresentWaitFeaturesKHR { features } + , VkPhysicalDevicePresentWait2FeaturesKHR { features } + , VkPhysicalDeviceRayQueryFeaturesKHR { features } + , VkPhysicalDeviceRayTracingMaintenance1FeaturesKHR { features } + , VkPhysicalDeviceRayTracingPipelineFeaturesKHR { features } + , VkPhysicalDeviceRayTracingPositionFetchFeaturesKHR { features } + , VkPhysicalDeviceRobustness2FeaturesKHR { features } + , VkPhysicalDeviceShaderBfloat16FeaturesKHR { features } + , VkPhysicalDeviceShaderClockFeaturesKHR { features } + , VkPhysicalDeviceShaderMaximalReconvergenceFeaturesKHR { features } + , VkPhysicalDeviceShaderQuadControlFeaturesKHR { features } + , VkPhysicalDeviceShaderRelaxedExtendedInstructionFeaturesKHR { features } + , VkPhysicalDeviceShaderSubgroupUniformControlFlowFeaturesKHR { features } + , VkPhysicalDeviceSwapchainMaintenance1FeaturesKHR { features } + , VkPhysicalDeviceUnifiedImageLayoutsFeaturesKHR { features } + , VkPhysicalDeviceVideoDecodeVP9FeaturesKHR { features } + , VkPhysicalDeviceVideoEncodeAV1FeaturesKHR { features } + , VkPhysicalDeviceVideoEncodeIntraRefreshFeaturesKHR { features } + , VkPhysicalDeviceVideoEncodeQuantizationMapFeaturesKHR { features } + , VkPhysicalDeviceVideoMaintenance1FeaturesKHR { features } + , VkPhysicalDeviceVideoMaintenance2FeaturesKHR { features } + , VkPhysicalDeviceWorkgroupMemoryExplicitLayoutFeaturesKHR { features } + , accelerationStructure { nullptr } + , accelerationStructureCaptureReplay { nullptr } + , accelerationStructureIndirectBuild { nullptr } + , accelerationStructureHostCommands { nullptr } + , descriptorBindingAccelerationStructureUpdateAfterBind { nullptr } + , computeDerivativeGroupQuads { nullptr } + , computeDerivativeGroupLinear { nullptr } + , cooperativeMatrix { nullptr } + , cooperativeMatrixRobustBufferAccess { nullptr } + , depthClampZeroOne { nullptr } + , fragmentShaderBarycentric { nullptr } + , pipelineFragmentShadingRate { nullptr } + , primitiveFragmentShadingRate { nullptr } + , attachmentFragmentShadingRate { nullptr } + , maintenance7 { nullptr } + , maintenance8 { nullptr } + , maintenance9 { nullptr } + , performanceCounterQueryPools { nullptr } + , performanceCounterMultipleQueryPools { nullptr } + , pipelineBinaries { nullptr } + , pipelineExecutableInfo { nullptr } + , presentId { nullptr } + , presentId2 { nullptr } + , presentModeFifoLatestReady { nullptr } + , presentWait { nullptr } + , presentWait2 { nullptr } + , rayQuery { nullptr } + , rayTracingMaintenance1 { nullptr } + , rayTracingPipelineTraceRaysIndirect2 { nullptr } + , rayTracingPipeline { nullptr } + , rayTracingPipelineShaderGroupHandleCaptureReplay { nullptr } + , rayTracingPipelineShaderGroupHandleCaptureReplayMixed { nullptr } + , rayTracingPipelineTraceRaysIndirect { nullptr } + , rayTraversalPrimitiveCulling { nullptr } + , rayTracingPositionFetch { nullptr } + , robustBufferAccess2 { nullptr } + , robustImageAccess2 { nullptr } + , nullDescriptor { nullptr } + , shaderBFloat16Type { nullptr } + , shaderBFloat16DotProduct { nullptr } + , shaderBFloat16CooperativeMatrix { nullptr } + , shaderSubgroupClock { nullptr } + , shaderDeviceClock { nullptr } + , shaderMaximalReconvergence { nullptr } + , shaderQuadControl { nullptr } + , shaderRelaxedExtendedInstruction { nullptr } + , shaderSubgroupUniformControlFlow { nullptr } + , swapchainMaintenance1 { nullptr } + , unifiedImageLayouts { nullptr } + , unifiedImageLayoutsVideo { nullptr } + , videoDecodeVP9 { nullptr } + , videoEncodeAV1 { nullptr } + , videoEncodeIntraRefresh { nullptr } + , videoEncodeQuantizationMap { nullptr } + , videoMaintenance1 { nullptr } + , videoMaintenance2 { nullptr } + , workgroupMemoryExplicitLayout { nullptr } + , workgroupMemoryExplicitLayoutScalarBlockLayout { nullptr } + , workgroupMemoryExplicitLayout8BitAccess { nullptr } + , workgroupMemoryExplicitLayout16BitAccess { nullptr } { + + _link(); + } + + /// + /// \brief Copy Assignment + /// \param features The features to copy + /// \returns A reference to \emph{this} + device_features_khr& operator=(const device_features_khr& features) { + if (this == &features) { + return *this; + } + + // Copy data + VkPhysicalDeviceAccelerationStructureFeaturesKHR::operator=(features); + VkPhysicalDeviceComputeShaderDerivativesFeaturesKHR::operator=(features); + VkPhysicalDeviceCooperativeMatrixFeaturesKHR::operator=(features); + VkPhysicalDeviceDepthClampZeroOneFeaturesKHR::operator=(features); + VkPhysicalDeviceFragmentShaderBarycentricFeaturesKHR::operator=(features); + VkPhysicalDeviceFragmentShadingRateFeaturesKHR::operator=(features); + VkPhysicalDeviceMaintenance7FeaturesKHR::operator=(features); + VkPhysicalDeviceMaintenance8FeaturesKHR::operator=(features); + VkPhysicalDeviceMaintenance9FeaturesKHR::operator=(features); + VkPhysicalDevicePerformanceQueryFeaturesKHR::operator=(features); + VkPhysicalDevicePipelineBinaryFeaturesKHR::operator=(features); + VkPhysicalDevicePipelineExecutablePropertiesFeaturesKHR::operator=(features); + VkPhysicalDevicePresentIdFeaturesKHR::operator=(features); + VkPhysicalDevicePresentId2FeaturesKHR::operator=(features); + VkPhysicalDevicePresentModeFifoLatestReadyFeaturesKHR::operator=(features); + VkPhysicalDevicePresentWaitFeaturesKHR::operator=(features); + VkPhysicalDevicePresentWait2FeaturesKHR::operator=(features); + VkPhysicalDeviceRayQueryFeaturesKHR::operator=(features); + VkPhysicalDeviceRayTracingMaintenance1FeaturesKHR::operator=(features); + VkPhysicalDeviceRayTracingPipelineFeaturesKHR::operator=(features); + VkPhysicalDeviceRayTracingPositionFetchFeaturesKHR::operator=(features); + VkPhysicalDeviceRobustness2FeaturesKHR::operator=(features); + VkPhysicalDeviceShaderBfloat16FeaturesKHR::operator=(features); + VkPhysicalDeviceShaderClockFeaturesKHR::operator=(features); + VkPhysicalDeviceShaderMaximalReconvergenceFeaturesKHR::operator=(features); + VkPhysicalDeviceShaderQuadControlFeaturesKHR::operator=(features); + VkPhysicalDeviceShaderRelaxedExtendedInstructionFeaturesKHR::operator=(features); + VkPhysicalDeviceShaderSubgroupUniformControlFlowFeaturesKHR::operator=(features); + VkPhysicalDeviceSwapchainMaintenance1FeaturesKHR::operator=(features); + VkPhysicalDeviceUnifiedImageLayoutsFeaturesKHR::operator=(features); + VkPhysicalDeviceVideoDecodeVP9FeaturesKHR::operator=(features); + VkPhysicalDeviceVideoEncodeAV1FeaturesKHR::operator=(features); + VkPhysicalDeviceVideoEncodeIntraRefreshFeaturesKHR::operator=(features); + VkPhysicalDeviceVideoEncodeQuantizationMapFeaturesKHR::operator=(features); + VkPhysicalDeviceVideoMaintenance1FeaturesKHR::operator=(features); + VkPhysicalDeviceVideoMaintenance2FeaturesKHR::operator=(features); + VkPhysicalDeviceWorkgroupMemoryExplicitLayoutFeaturesKHR::operator=(features); + + _link(); + + return *this; + } + + /// + /// \brief Chain an extension structure + /// \param next + void chain(void* next) { + VkPhysicalDeviceWorkgroupMemoryExplicitLayoutFeaturesKHR::pNext = next; + } + + /// + /// \brief Implicit casting for chaining + operator void*() { + return static_cast(this); + } + + +// Helpers ------------------------------------------------------------------------------------------------------------- +private: + + void _clear() { + + // Clear out the struct + fennec::memset(this, 0, sizeof(*this)); + + // Set structure types + VkPhysicalDeviceAccelerationStructureFeaturesKHR::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_ACCELERATION_STRUCTURE_FEATURES_KHR; + VkPhysicalDeviceComputeShaderDerivativesFeaturesKHR::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_COMPUTE_SHADER_DERIVATIVES_FEATURES_KHR; + VkPhysicalDeviceCooperativeMatrixFeaturesKHR::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_COOPERATIVE_MATRIX_FEATURES_KHR; + VkPhysicalDeviceDepthClampZeroOneFeaturesKHR::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_DEPTH_CLAMP_ZERO_ONE_FEATURES_KHR; + VkPhysicalDeviceFragmentShaderBarycentricFeaturesKHR::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_FRAGMENT_SHADER_BARYCENTRIC_FEATURES_KHR; + VkPhysicalDeviceFragmentShadingRateFeaturesKHR::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_FRAGMENT_SHADING_RATE_FEATURES_KHR; + VkPhysicalDeviceMaintenance7FeaturesKHR::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_MAINTENANCE_7_FEATURES_KHR; + VkPhysicalDeviceMaintenance8FeaturesKHR::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_MAINTENANCE_8_FEATURES_KHR; + VkPhysicalDeviceMaintenance9FeaturesKHR::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_MAINTENANCE_9_FEATURES_KHR; + VkPhysicalDevicePerformanceQueryFeaturesKHR::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_PERFORMANCE_QUERY_FEATURES_KHR; + VkPhysicalDevicePipelineBinaryFeaturesKHR::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_PIPELINE_BINARY_FEATURES_KHR; + VkPhysicalDevicePipelineExecutablePropertiesFeaturesKHR::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_PIPELINE_EXECUTABLE_PROPERTIES_FEATURES_KHR; + VkPhysicalDevicePresentIdFeaturesKHR::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_PRESENT_ID_FEATURES_KHR; + VkPhysicalDevicePresentId2FeaturesKHR::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_PRESENT_ID_2_FEATURES_KHR; + VkPhysicalDevicePresentModeFifoLatestReadyFeaturesKHR::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_PRESENT_MODE_FIFO_LATEST_READY_FEATURES_KHR; + VkPhysicalDevicePresentWaitFeaturesKHR::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_PRESENT_WAIT_FEATURES_KHR; + VkPhysicalDevicePresentWait2FeaturesKHR::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_PRESENT_WAIT_2_FEATURES_KHR; + VkPhysicalDeviceRayQueryFeaturesKHR::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_RAY_QUERY_FEATURES_KHR; + VkPhysicalDeviceRayTracingMaintenance1FeaturesKHR::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_RAY_TRACING_MAINTENANCE_1_FEATURES_KHR; + VkPhysicalDeviceRayTracingPipelineFeaturesKHR::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_RAY_TRACING_PIPELINE_FEATURES_KHR; + VkPhysicalDeviceRayTracingPositionFetchFeaturesKHR::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_RAY_TRACING_POSITION_FETCH_FEATURES_KHR; + VkPhysicalDeviceRobustness2FeaturesKHR::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_ROBUSTNESS_2_FEATURES_KHR; + VkPhysicalDeviceShaderBfloat16FeaturesKHR::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SHADER_BFLOAT16_FEATURES_KHR; + VkPhysicalDeviceShaderClockFeaturesKHR::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SHADER_CLOCK_FEATURES_KHR; + VkPhysicalDeviceShaderMaximalReconvergenceFeaturesKHR::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SHADER_MAXIMAL_RECONVERGENCE_FEATURES_KHR; + VkPhysicalDeviceShaderQuadControlFeaturesKHR::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SHADER_QUAD_CONTROL_FEATURES_KHR; + VkPhysicalDeviceShaderRelaxedExtendedInstructionFeaturesKHR::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SHADER_RELAXED_EXTENDED_INSTRUCTION_FEATURES_KHR; + VkPhysicalDeviceShaderSubgroupUniformControlFlowFeaturesKHR::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SHADER_SUBGROUP_UNIFORM_CONTROL_FLOW_FEATURES_KHR; + VkPhysicalDeviceSwapchainMaintenance1FeaturesKHR::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SWAPCHAIN_MAINTENANCE_1_FEATURES_KHR; + VkPhysicalDeviceUnifiedImageLayoutsFeaturesKHR::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_UNIFIED_IMAGE_LAYOUTS_FEATURES_KHR; + VkPhysicalDeviceVideoDecodeVP9FeaturesKHR::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_VIDEO_DECODE_VP9_FEATURES_KHR; + VkPhysicalDeviceVideoEncodeAV1FeaturesKHR::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_VIDEO_ENCODE_AV1_FEATURES_KHR; + VkPhysicalDeviceVideoEncodeIntraRefreshFeaturesKHR::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_VIDEO_ENCODE_INTRA_REFRESH_FEATURES_KHR; + VkPhysicalDeviceVideoEncodeQuantizationMapFeaturesKHR::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_VIDEO_ENCODE_QUANTIZATION_MAP_FEATURES_KHR; + VkPhysicalDeviceVideoMaintenance1FeaturesKHR::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_VIDEO_MAINTENANCE_1_FEATURES_KHR; + VkPhysicalDeviceVideoMaintenance2FeaturesKHR::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_VIDEO_MAINTENANCE_2_FEATURES_KHR; + VkPhysicalDeviceWorkgroupMemoryExplicitLayoutFeaturesKHR::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_WORKGROUP_MEMORY_EXPLICIT_LAYOUT_FEATURES_KHR; + } + + void _link() { + + + // Bind to Features structures + accelerationStructure = &(VkPhysicalDeviceAccelerationStructureFeaturesKHR::accelerationStructure); + accelerationStructureCaptureReplay = &(VkPhysicalDeviceAccelerationStructureFeaturesKHR::accelerationStructureCaptureReplay); + accelerationStructureIndirectBuild = &(VkPhysicalDeviceAccelerationStructureFeaturesKHR::accelerationStructureIndirectBuild); + accelerationStructureHostCommands = &(VkPhysicalDeviceAccelerationStructureFeaturesKHR::accelerationStructureHostCommands); + descriptorBindingAccelerationStructureUpdateAfterBind = &(VkPhysicalDeviceAccelerationStructureFeaturesKHR::accelerationStructureHostCommands); + computeDerivativeGroupQuads = &(VkPhysicalDeviceComputeShaderDerivativesFeaturesKHR::computeDerivativeGroupQuads); + computeDerivativeGroupLinear = &(VkPhysicalDeviceComputeShaderDerivativesFeaturesKHR::computeDerivativeGroupLinear); + cooperativeMatrix = &(VkPhysicalDeviceCooperativeMatrixFeaturesKHR::cooperativeMatrix); + cooperativeMatrixRobustBufferAccess = &(VkPhysicalDeviceCooperativeMatrixFeaturesKHR::cooperativeMatrixRobustBufferAccess); + depthClampZeroOne = &(VkPhysicalDeviceDepthClampZeroOneFeaturesKHR::depthClampZeroOne); + fragmentShaderBarycentric = &(VkPhysicalDeviceFragmentShaderBarycentricFeaturesKHR::fragmentShaderBarycentric); + pipelineFragmentShadingRate = &(VkPhysicalDeviceFragmentShadingRateFeaturesKHR::pipelineFragmentShadingRate); + primitiveFragmentShadingRate = &(VkPhysicalDeviceFragmentShadingRateFeaturesKHR::primitiveFragmentShadingRate); + attachmentFragmentShadingRate = &(VkPhysicalDeviceFragmentShadingRateFeaturesKHR::attachmentFragmentShadingRate); + maintenance7 = &(VkPhysicalDeviceMaintenance7FeaturesKHR::maintenance7); + maintenance8 = &(VkPhysicalDeviceMaintenance8FeaturesKHR::maintenance8); + maintenance9 = &(VkPhysicalDeviceMaintenance9FeaturesKHR::maintenance9); + performanceCounterQueryPools = &(VkPhysicalDevicePerformanceQueryFeaturesKHR::performanceCounterQueryPools); + performanceCounterMultipleQueryPools = &(VkPhysicalDevicePerformanceQueryFeaturesKHR::performanceCounterMultipleQueryPools); + pipelineBinaries = &(VkPhysicalDevicePipelineBinaryFeaturesKHR::pipelineBinaries); + pipelineExecutableInfo = &(VkPhysicalDevicePipelineExecutablePropertiesFeaturesKHR::pipelineExecutableInfo); + presentId = &(VkPhysicalDevicePresentIdFeaturesKHR::presentId); + presentId2 = &(VkPhysicalDevicePresentId2FeaturesKHR::presentId2); + presentModeFifoLatestReady = &(VkPhysicalDevicePresentModeFifoLatestReadyFeaturesKHR::presentModeFifoLatestReady); + presentWait = &(VkPhysicalDevicePresentWaitFeaturesKHR::presentWait); + presentWait2 = &(VkPhysicalDevicePresentWait2FeaturesKHR::presentWait2); + rayQuery = &(VkPhysicalDeviceRayQueryFeaturesKHR::rayQuery); + rayTracingMaintenance1 = &(VkPhysicalDeviceRayTracingMaintenance1FeaturesKHR::rayTracingMaintenance1); + rayTracingPipelineTraceRaysIndirect2 = &(VkPhysicalDeviceRayTracingMaintenance1FeaturesKHR::rayTracingPipelineTraceRaysIndirect2); + rayTracingPipeline = &(VkPhysicalDeviceRayTracingPipelineFeaturesKHR::rayTracingPipeline); + rayTracingPipelineShaderGroupHandleCaptureReplay = &(VkPhysicalDeviceRayTracingPipelineFeaturesKHR::rayTracingPipelineShaderGroupHandleCaptureReplay); + rayTracingPipelineShaderGroupHandleCaptureReplayMixed = &(VkPhysicalDeviceRayTracingPipelineFeaturesKHR::rayTracingPipelineShaderGroupHandleCaptureReplayMixed); + rayTracingPipelineTraceRaysIndirect = &(VkPhysicalDeviceRayTracingPipelineFeaturesKHR::rayTracingPipelineTraceRaysIndirect); + rayTraversalPrimitiveCulling = &(VkPhysicalDeviceRayTracingPipelineFeaturesKHR::rayTraversalPrimitiveCulling); + rayTracingPositionFetch = &(VkPhysicalDeviceRayTracingPositionFetchFeaturesKHR::rayTracingPositionFetch); + robustBufferAccess2 = &(VkPhysicalDeviceRobustness2FeaturesKHR::robustBufferAccess2); + robustImageAccess2 = &(VkPhysicalDeviceRobustness2FeaturesKHR::robustImageAccess2); + nullDescriptor = &(VkPhysicalDeviceRobustness2FeaturesKHR::nullDescriptor); + shaderBFloat16Type = &(VkPhysicalDeviceShaderBfloat16FeaturesKHR::shaderBFloat16Type); + shaderBFloat16DotProduct = &(VkPhysicalDeviceShaderBfloat16FeaturesKHR::shaderBFloat16DotProduct); + shaderBFloat16CooperativeMatrix = &(VkPhysicalDeviceShaderBfloat16FeaturesKHR::shaderBFloat16CooperativeMatrix); + shaderSubgroupClock = &(VkPhysicalDeviceShaderClockFeaturesKHR::shaderSubgroupClock); + shaderDeviceClock = &(VkPhysicalDeviceShaderClockFeaturesKHR::shaderDeviceClock); + shaderMaximalReconvergence = &(VkPhysicalDeviceShaderMaximalReconvergenceFeaturesKHR::shaderMaximalReconvergence); + shaderQuadControl = &(VkPhysicalDeviceShaderQuadControlFeaturesKHR::shaderQuadControl); + shaderRelaxedExtendedInstruction = &(VkPhysicalDeviceShaderRelaxedExtendedInstructionFeaturesKHR::shaderRelaxedExtendedInstruction); + shaderSubgroupUniformControlFlow = &(VkPhysicalDeviceShaderSubgroupUniformControlFlowFeaturesKHR::shaderSubgroupUniformControlFlow); + swapchainMaintenance1 = &(VkPhysicalDeviceSwapchainMaintenance1FeaturesKHR::swapchainMaintenance1); + unifiedImageLayouts = &(VkPhysicalDeviceUnifiedImageLayoutsFeaturesKHR::unifiedImageLayouts); + unifiedImageLayoutsVideo = &(VkPhysicalDeviceUnifiedImageLayoutsFeaturesKHR::unifiedImageLayoutsVideo); + videoDecodeVP9 = &(VkPhysicalDeviceVideoDecodeVP9FeaturesKHR::videoDecodeVP9); + videoEncodeAV1 = &(VkPhysicalDeviceVideoEncodeAV1FeaturesKHR::videoEncodeAV1); + videoEncodeIntraRefresh = &(VkPhysicalDeviceVideoEncodeIntraRefreshFeaturesKHR::videoEncodeIntraRefresh); + videoEncodeQuantizationMap = &(VkPhysicalDeviceVideoEncodeQuantizationMapFeaturesKHR::videoEncodeQuantizationMap); + videoMaintenance1 = &(VkPhysicalDeviceVideoMaintenance1FeaturesKHR::videoMaintenance1); + videoMaintenance2 = &(VkPhysicalDeviceVideoMaintenance2FeaturesKHR::videoMaintenance2); + workgroupMemoryExplicitLayout = &(VkPhysicalDeviceWorkgroupMemoryExplicitLayoutFeaturesKHR::workgroupMemoryExplicitLayout); + workgroupMemoryExplicitLayoutScalarBlockLayout = &(VkPhysicalDeviceWorkgroupMemoryExplicitLayoutFeaturesKHR::workgroupMemoryExplicitLayoutScalarBlockLayout); + workgroupMemoryExplicitLayout8BitAccess = &(VkPhysicalDeviceWorkgroupMemoryExplicitLayoutFeaturesKHR::workgroupMemoryExplicitLayout8BitAccess); + workgroupMemoryExplicitLayout16BitAccess = &(VkPhysicalDeviceWorkgroupMemoryExplicitLayoutFeaturesKHR::workgroupMemoryExplicitLayout16BitAccess); + + + // Daisy Chain + VkPhysicalDeviceAccelerationStructureFeaturesKHR::pNext = static_cast(this); + VkPhysicalDeviceComputeShaderDerivativesFeaturesKHR::pNext = static_cast(this); + VkPhysicalDeviceCooperativeMatrixFeaturesKHR::pNext = static_cast(this); + VkPhysicalDeviceDepthClampZeroOneFeaturesKHR::pNext = static_cast(this); + VkPhysicalDeviceFragmentShaderBarycentricFeaturesKHR::pNext = static_cast(this); + VkPhysicalDeviceFragmentShadingRateFeaturesKHR::pNext = static_cast(this); + VkPhysicalDeviceMaintenance7FeaturesKHR::pNext = static_cast(this); + VkPhysicalDeviceMaintenance8FeaturesKHR::pNext = static_cast(this); + VkPhysicalDeviceMaintenance9FeaturesKHR::pNext = static_cast(this); + VkPhysicalDevicePerformanceQueryFeaturesKHR::pNext = static_cast(this); + VkPhysicalDevicePipelineBinaryFeaturesKHR::pNext = static_cast(this); + VkPhysicalDevicePipelineExecutablePropertiesFeaturesKHR::pNext = static_cast(this); + VkPhysicalDevicePresentIdFeaturesKHR::pNext = static_cast(this); + VkPhysicalDevicePresentId2FeaturesKHR::pNext = static_cast(this); + VkPhysicalDevicePresentModeFifoLatestReadyFeaturesKHR::pNext = static_cast(this); + VkPhysicalDevicePresentWaitFeaturesKHR::pNext = static_cast(this); + VkPhysicalDevicePresentWait2FeaturesKHR::pNext = static_cast(this); + VkPhysicalDeviceRayQueryFeaturesKHR::pNext = static_cast(this); + VkPhysicalDeviceRayTracingMaintenance1FeaturesKHR::pNext = static_cast(this); + VkPhysicalDeviceRayTracingPipelineFeaturesKHR::pNext = static_cast(this); + VkPhysicalDeviceRayTracingPositionFetchFeaturesKHR::pNext = static_cast(this); + VkPhysicalDeviceRobustness2FeaturesKHR::pNext = static_cast(this); + VkPhysicalDeviceShaderBfloat16FeaturesKHR::pNext = static_cast(this); + VkPhysicalDeviceShaderClockFeaturesKHR::pNext = static_cast(this); + VkPhysicalDeviceShaderMaximalReconvergenceFeaturesKHR::pNext = static_cast(this); + VkPhysicalDeviceShaderQuadControlFeaturesKHR::pNext = static_cast(this); + VkPhysicalDeviceShaderRelaxedExtendedInstructionFeaturesKHR::pNext = static_cast(this); + VkPhysicalDeviceShaderSubgroupUniformControlFlowFeaturesKHR::pNext = static_cast(this); + VkPhysicalDeviceSwapchainMaintenance1FeaturesKHR::pNext = static_cast(this); + VkPhysicalDeviceUnifiedImageLayoutsFeaturesKHR::pNext = static_cast(this); + VkPhysicalDeviceVideoDecodeVP9FeaturesKHR::pNext = static_cast(this); + VkPhysicalDeviceVideoEncodeAV1FeaturesKHR::pNext = static_cast(this); + VkPhysicalDeviceVideoEncodeIntraRefreshFeaturesKHR::pNext = static_cast(this); + VkPhysicalDeviceVideoEncodeQuantizationMapFeaturesKHR::pNext = static_cast(this); + VkPhysicalDeviceVideoMaintenance1FeaturesKHR::pNext = static_cast(this); + VkPhysicalDeviceVideoMaintenance2FeaturesKHR::pNext = static_cast(this); + VkPhysicalDeviceWorkgroupMemoryExplicitLayoutFeaturesKHR::pNext = nullptr; + } +}; + +/// +/// \brief EXT Features +struct device_features_ext : private VkPhysicalDeviceASTCDecodeFeaturesEXT, + private VkPhysicalDeviceAddressBindingReportFeaturesEXT, + private VkPhysicalDeviceAttachmentFeedbackLoopDynamicStateFeaturesEXT, + private VkPhysicalDeviceAttachmentFeedbackLoopLayoutFeaturesEXT, + private VkPhysicalDeviceBlendOperationAdvancedFeaturesEXT, + private VkPhysicalDeviceBorderColorSwizzleFeaturesEXT, + private VkPhysicalDeviceBufferDeviceAddressFeaturesEXT, + private VkPhysicalDevice4444FormatsFeaturesEXT, + private VkPhysicalDeviceColorWriteEnableFeaturesEXT, + private VkPhysicalDeviceConditionalRenderingFeaturesEXT, + private VkPhysicalDeviceCustomBorderColorFeaturesEXT, + private VkPhysicalDeviceDepthBiasControlFeaturesEXT, + private VkPhysicalDeviceDepthClampControlFeaturesEXT, + private VkPhysicalDeviceDepthClipControlFeaturesEXT, + private VkPhysicalDeviceDepthClipEnableFeaturesEXT, + private VkPhysicalDeviceDescriptorBufferFeaturesEXT, + private VkPhysicalDeviceDeviceGeneratedCommandsFeaturesEXT, + private VkPhysicalDeviceDeviceMemoryReportFeaturesEXT, + private VkPhysicalDeviceDynamicRenderingUnusedAttachmentsFeaturesEXT, + private VkPhysicalDeviceExtendedDynamicStateFeaturesEXT, + private VkPhysicalDeviceExtendedDynamicState2FeaturesEXT, + private VkPhysicalDeviceExtendedDynamicState3FeaturesEXT, + private VkPhysicalDeviceFaultFeaturesEXT, + private VkPhysicalDeviceFragmentDensityMapFeaturesEXT, + private VkPhysicalDeviceFragmentDensityMap2FeaturesEXT, + private VkPhysicalDeviceFragmentDensityMapOffsetFeaturesEXT, + private VkPhysicalDeviceFragmentShaderInterlockFeaturesEXT, + private VkPhysicalDeviceFrameBoundaryFeaturesEXT, + private VkPhysicalDeviceGraphicsPipelineLibraryFeaturesEXT, + private VkPhysicalDeviceImage2DViewOf3DFeaturesEXT, + private VkPhysicalDeviceImageCompressionControlFeaturesEXT, + private VkPhysicalDeviceImageCompressionControlSwapchainFeaturesEXT, + private VkPhysicalDeviceImageSlicedViewOf3DFeaturesEXT, + private VkPhysicalDeviceImageViewMinLodFeaturesEXT, + private VkPhysicalDeviceLegacyDitheringFeaturesEXT, + private VkPhysicalDeviceLegacyVertexAttributesFeaturesEXT, + private VkPhysicalDeviceMapMemoryPlacedFeaturesEXT, + private VkPhysicalDeviceMemoryPriorityFeaturesEXT, + private VkPhysicalDeviceMeshShaderFeaturesEXT, + private VkPhysicalDeviceMultiDrawFeaturesEXT, + private VkPhysicalDeviceMultisampledRenderToSingleSampledFeaturesEXT, + private VkPhysicalDeviceMutableDescriptorTypeFeaturesEXT, + private VkPhysicalDeviceNestedCommandBufferFeaturesEXT, + private VkPhysicalDeviceNonSeamlessCubeMapFeaturesEXT, + private VkPhysicalDeviceOpacityMicromapFeaturesEXT, + private VkPhysicalDevicePageableDeviceLocalMemoryFeaturesEXT, + private VkPhysicalDevicePipelineLibraryGroupHandlesFeaturesEXT, + private VkPhysicalDevicePipelinePropertiesFeaturesEXT, + private VkPhysicalDevicePrimitiveTopologyListRestartFeaturesEXT, + private VkPhysicalDevicePrimitivesGeneratedQueryFeaturesEXT, + private VkPhysicalDeviceProvokingVertexFeaturesEXT, + private VkPhysicalDeviceRGBA10X6FormatsFeaturesEXT, + private VkPhysicalDeviceRasterizationOrderAttachmentAccessFeaturesEXT, + private VkPhysicalDeviceShaderAtomicFloatFeaturesEXT, + private VkPhysicalDeviceShaderAtomicFloat2FeaturesEXT, + private VkPhysicalDeviceShaderFloat8FeaturesEXT, + private VkPhysicalDeviceShaderImageAtomicInt64FeaturesEXT, + private VkPhysicalDeviceShaderModuleIdentifierFeaturesEXT, + private VkPhysicalDeviceShaderObjectFeaturesEXT, + private VkPhysicalDeviceShaderReplicatedCompositesFeaturesEXT, + private VkPhysicalDeviceShaderTileImageFeaturesEXT, + private VkPhysicalDeviceSubpassMergeFeedbackFeaturesEXT, + private VkPhysicalDeviceTexelBufferAlignmentFeaturesEXT, + private VkPhysicalDeviceTransformFeedbackFeaturesEXT, + private VkPhysicalDeviceVertexAttributeRobustnessFeaturesEXT, + private VkPhysicalDeviceVertexInputDynamicStateFeaturesEXT, + private VkPhysicalDeviceYcbcr2Plane444FormatsFeaturesEXT, + private VkPhysicalDeviceYcbcrImageArraysFeaturesEXT, + private VkPhysicalDeviceZeroInitializeDeviceMemoryFeaturesEXT { + +// Public References --------------------------------------------------------------------------------------------------- +public: + + /// \name Features + /// @{ + + VkBool32* decodeModeSharedExponent; //!< Decode Mode Shared Exponent + VkBool32* reportAddressBinding; //!< Report Address Binding + VkBool32* attachmentFeedbackLoopDynamicState; //!< Attachment Feedback Loop Dynamic State + VkBool32* attachmentFeedbackLoopLayout; //!< Attachment Feedback Loop Layout + VkBool32* advancedBlendCoherentOperations; //!< Advanced Blend Coherent Operations + VkBool32* borderColorSwizzle; //!< Border Color Swizzle + VkBool32* borderColorSwizzleFromImage; //!< Border Color Swizzle From Image + VkBool32* bufferDeviceAddress; //!< Buffer Device Address + VkBool32* bufferDeviceAddressCaptureReplay; //!< Buffer Device Address Capture Replay + VkBool32* bufferDeviceAddressMultiDevice; //!< Buffer Device Address Multi Device + VkBool32* formatA4R4G4B4; //!< Format A4 R4 G4 B4 + VkBool32* formatA4B4G4R4; //!< Format A4 B4 G4 R4 + VkBool32* colorWriteEnable; //!< Color Write Enable + VkBool32* conditionalRendering; //!< Conditional Rendering + VkBool32* inheritedConditionalRendering; //!< Inherited Conditional Rendering + VkBool32* customBorderColors; //!< Custom Border Colors + VkBool32* customBorderColorWithoutFormat; //!< Custom Border Color Without Format + VkBool32* depthBiasControl; //!< Depth Bias Control + VkBool32* leastRepresentableValueForceUnormRepresentation; //!< Least Representable Value Force Unorm Representation + VkBool32* floatRepresentation; //!< Float Representation + VkBool32* depthBiasExact; //!< Depth Bias Exact + VkBool32* depthClampControl; //!< Depth Clamp Control + VkBool32* depthClipControl; //!< Depth Clip Control + VkBool32* depthClipEnable; //!< Depth Clip Enable + VkBool32* descriptorBuffer; //!< Descriptor Buffer + VkBool32* descriptorBufferCaptureReplay; //!< Descriptor Buffer Capture Replay + VkBool32* descriptorBufferImageLayoutIgnored; //!< Descriptor Buffer Image Layout Ignored + VkBool32* descriptorBufferPushDescriptors; //!< Descriptor Buffer Push Descriptors + VkBool32* deviceGeneratedCommands; //!< Device Generated Commands + VkBool32* dynamicGeneratedPipelineLayout; //!< Dynamic Generated Pipeline Layout + VkBool32* deviceMemoryReport; //!< Device Memory Report + VkBool32* dynamicRenderingUnusedAttachments; //!< Dynamic Rendering Unused Attachments + VkBool32* extendedDynamicState; //!< Extended Dynamic State + VkBool32* extendedDynamicState2; //!< Extended Dynamic State2 + VkBool32* extendedDynamicState2LogicOp; //!< Extended Dynamic State2 Logic Op + VkBool32* extendedDynamicState2PatchControlPoints; //!< Extended Dynamic State2 Patch Control Points + VkBool32* extendedDynamicState3TessellationDomainOrigin; //!< Extended Dynamic State3 Tessellation Domain Origin + VkBool32* extendedDynamicState3DepthClampEnable; //!< Extended Dynamic State3 Depth Clamp Enable + VkBool32* extendedDynamicState3PolygonMode; //!< Extended Dynamic State3 Polygon Mode + VkBool32* extendedDynamicState3RasterizationSamples; //!< Extended Dynamic State3 Rasterization Samples + VkBool32* extendedDynamicState3SampleMask; //!< Extended Dynamic State3 Sample Mask + VkBool32* extendedDynamicState3AlphaToCoverageEnable; //!< Extended Dynamic State3 Alpha To Coverage Enable + VkBool32* extendedDynamicState3AlphaToOneEnable; //!< Extended Dynamic State3 Alpha To One Enable + VkBool32* extendedDynamicState3LogicOpEnable; //!< Extended Dynamic State3 Logic Op Enable + VkBool32* extendedDynamicState3ColorBlendEnable; //!< Extended Dynamic State3 Color Blend Enable + VkBool32* extendedDynamicState3ColorBlendEquation; //!< Extended Dynamic State3 Color Blend Equation + VkBool32* extendedDynamicState3ColorWriteMask; //!< Extended Dynamic State3 Color Write Mask + VkBool32* extendedDynamicState3RasterizationStream; //!< Extended Dynamic State3 Rasterization Stream + VkBool32* extendedDynamicState3ConservativeRasterizationMode; //!< Extended Dynamic State3 Conservative Rasterization Mode + VkBool32* extendedDynamicState3ExtraPrimitiveOverestimationSize; //!< Extended Dynamic State3 Extra Primitive Overestimation Size + VkBool32* extendedDynamicState3DepthClipEnable; //!< Extended Dynamic State3 Depth Clip Enable + VkBool32* extendedDynamicState3SampleLocationsEnable; //!< Extended Dynamic State3 Sample Locations Enable + VkBool32* extendedDynamicState3ColorBlendAdvanced; //!< Extended Dynamic State3 Color Blend Advanced + VkBool32* extendedDynamicState3ProvokingVertexMode; //!< Extended Dynamic State3 Provoking Vertex Mode + VkBool32* extendedDynamicState3LineRasterizationMode; //!< Extended Dynamic State3 Line Rasterization Mode + VkBool32* extendedDynamicState3LineStippleEnable; //!< Extended Dynamic State3 Line Stipple Enable + VkBool32* extendedDynamicState3DepthClipNegativeOneToOne; //!< Extended Dynamic State3 Depth Clip Negative One To One + VkBool32* extendedDynamicState3ViewportWScalingEnable; //!< Extended Dynamic State3 Viewport W Scaling Enable + VkBool32* extendedDynamicState3ViewportSwizzle; //!< Extended Dynamic State3 Viewport Swizzle + VkBool32* extendedDynamicState3CoverageToColorEnable; //!< Extended Dynamic State3 Coverage To Color Enable + VkBool32* extendedDynamicState3CoverageToColorLocation; //!< Extended Dynamic State3 Coverage To Color Location + VkBool32* extendedDynamicState3CoverageModulationMode; //!< Extended Dynamic State3 Coverage Modulation Mode + VkBool32* extendedDynamicState3CoverageModulationTableEnable; //!< Extended Dynamic State3 Coverage Modulation Table Enable + VkBool32* extendedDynamicState3CoverageModulationTable; //!< Extended Dynamic State3 Coverage Modulation Table + VkBool32* extendedDynamicState3CoverageReductionMode; //!< Extended Dynamic State3 Coverage Reduction Mode + VkBool32* extendedDynamicState3RepresentativeFragmentTestEnable; //!< Extended Dynamic State3 Representative Fragment Test Enable + VkBool32* extendedDynamicState3ShadingRateImageEnable; //!< Extended Dynamic State3 Shading Rate Image Enable + VkBool32* deviceFault; //!< Device Fault + VkBool32* deviceFaultVendorBinary; //!< Device Fault Vendor Binary + VkBool32* fragmentDensityMap; //!< Fragment Density Map + VkBool32* fragmentDensityMapDynamic; //!< Fragment Density Map Dynamic + VkBool32* fragmentDensityMapNonSubsampledImages; //!< Fragment Density Map Non Subsampled Images + VkBool32* fragmentDensityMapDeferred; //!< Fragment Density Map Deferred + VkBool32* fragmentDensityMapOffset; //!< Fragment Density Map Offset + VkBool32* fragmentShaderSampleInterlock; //!< Fragment Shader Sample Interlock + VkBool32* fragmentShaderPixelInterlock; //!< Fragment Shader Pixel Interlock + VkBool32* fragmentShaderShadingRateInterlock; //!< Fragment Shader Shading Rate Interlock + VkBool32* frameBoundary; //!< Frame Boundary + VkBool32* graphicsPipelineLibrary; //!< Graphics Pipeline Library + VkBool32* image2DViewOf3D; //!< Image2 D View Of3 D + VkBool32* sampler2DViewOf3D; //!< Sampler2 D View Of3 D + VkBool32* imageCompressionControl; //!< Image Compression Control + VkBool32* imageCompressionControlSwapchain; //!< Image Compression Control Swapchain + VkBool32* imageSlicedViewOf3D; //!< Image Sliced View Of3 D + VkBool32* imageMinLod; //!< Image Min Lod + VkBool32* legacyDithering; //!< Legacy Dithering + VkBool32* legacyVertexAttributes; //!< Legacy Vertex Attributes + VkBool32* memoryMapPlaced; //!< Memory Map Placed + VkBool32* memoryMapRangePlaced; //!< Memory Map Range Placed + VkBool32* memoryUnmapReserve; //!< Memory Unmap Reserve + VkBool32* memoryPriority; //!< Memory Priority + VkBool32* taskShader; //!< Task Shader + VkBool32* meshShader; //!< Mesh Shader + VkBool32* multiviewMeshShader; //!< Multiview Mesh Shader + VkBool32* primitiveFragmentShadingRateMeshShader; //!< Primitive Fragment Shading Rate Mesh Shader + VkBool32* meshShaderQueries; //!< Mesh Shader Queries + VkBool32* multiDraw; //!< Multi Draw + VkBool32* multisampledRenderToSingleSampled; //!< Multisampled Render To Single Sampled + VkBool32* mutableDescriptorType; //!< Mutable Descriptor Type + VkBool32* nestedCommandBuffer; //!< Nested Command Buffer + VkBool32* nestedCommandBufferRendering; //!< Nested Command Buffer Rendering + VkBool32* nestedCommandBufferSimultaneousUse; //!< Nested Command Buffer Simultaneous Use + VkBool32* nonSeamlessCubeMap; //!< Non Seamless Cube Map + VkBool32* micromap; //!< Micromap + VkBool32* micromapCaptureReplay; //!< Micromap Capture Replay + VkBool32* micromapHostCommands; //!< Micromap Host Commands + VkBool32* pageableDeviceLocalMemory; //!< Pageable Device Local Memory + VkBool32* pipelineLibraryGroupHandles; //!< Pipeline Library Group Handles + VkBool32* pipelinePropertiesIdentifier; //!< Pipeline Properties Identifier + VkBool32* primitiveTopologyListRestart; //!< Primitive Topology List Restart + VkBool32* primitiveTopologyPatchListRestart; //!< Primitive Topology Patch List Restart + VkBool32* primitivesGeneratedQuery; //!< Primitives Generated Query + VkBool32* primitivesGeneratedQueryWithRasterizerDiscard; //!< Primitives Generated Query With Rasterizer Discard + VkBool32* primitivesGeneratedQueryWithNonZeroStreams; //!< Primitives Generated Query With Non Zero Streams + VkBool32* provokingVertexLast; //!< Provoking Vertex Last + VkBool32* transformFeedbackPreservesProvokingVertex; //!< Transform Feedback Preserves Provoking Vertex + VkBool32* formatRgba10x6WithoutYCbCrSampler; //!< Format Rgba10x6 Without Y Cb Cr Sampler + VkBool32* rasterizationOrderColorAttachmentAccess; //!< Rasterization Order Color Attachment Access + VkBool32* rasterizationOrderDepthAttachmentAccess; //!< Rasterization Order Depth Attachment Access + VkBool32* rasterizationOrderStencilAttachmentAccess; //!< Rasterization Order Stencil Attachment Access + VkBool32* shaderBufferFloat32Atomics; //!< Shader Buffer Float32 Atomics + VkBool32* shaderBufferFloat32AtomicAdd; //!< Shader Buffer Float32 Atomic Add + VkBool32* shaderBufferFloat64Atomics; //!< Shader Buffer Float64 Atomics + VkBool32* shaderBufferFloat64AtomicAdd; //!< Shader Buffer Float64 Atomic Add + VkBool32* shaderSharedFloat32Atomics; //!< Shader Shared Float32 Atomics + VkBool32* shaderSharedFloat32AtomicAdd; //!< Shader Shared Float32 Atomic Add + VkBool32* shaderSharedFloat64Atomics; //!< Shader Shared Float64 Atomics + VkBool32* shaderSharedFloat64AtomicAdd; //!< Shader Shared Float64 Atomic Add + VkBool32* shaderImageFloat32Atomics; //!< Shader Image Float32 Atomics + VkBool32* shaderImageFloat32AtomicAdd; //!< Shader Image Float32 Atomic Add + VkBool32* sparseImageFloat32Atomics; //!< Sparse Image Float32 Atomics + VkBool32* sparseImageFloat32AtomicAdd; //!< Sparse Image Float32 Atomic Add + VkBool32* shaderBufferFloat16Atomics; //!< Shader Buffer Float16 Atomics + VkBool32* shaderBufferFloat16AtomicAdd; //!< Shader Buffer Float16 Atomic Add + VkBool32* shaderBufferFloat16AtomicMinMax; //!< Shader Buffer Float16 Atomic Min Max + VkBool32* shaderBufferFloat32AtomicMinMax; //!< Shader Buffer Float32 Atomic Min Max + VkBool32* shaderBufferFloat64AtomicMinMax; //!< Shader Buffer Float64 Atomic Min Max + VkBool32* shaderSharedFloat16Atomics; //!< Shader Shared Float16 Atomics + VkBool32* shaderSharedFloat16AtomicAdd; //!< Shader Shared Float16 Atomic Add + VkBool32* shaderSharedFloat16AtomicMinMax; //!< Shader Shared Float16 Atomic Min Max + VkBool32* shaderSharedFloat32AtomicMinMax; //!< Shader Shared Float32 Atomic Min Max + VkBool32* shaderSharedFloat64AtomicMinMax; //!< Shader Shared Float64 Atomic Min Max + VkBool32* shaderImageFloat32AtomicMinMax; //!< Shader Image Float32 Atomic Min Max + VkBool32* sparseImageFloat32AtomicMinMax; //!< Sparse Image Float32 Atomic Min Max + VkBool32* shaderFloat8; //!< Shader Float8 + VkBool32* shaderFloat8CooperativeMatrix; //!< Shader Float8 Cooperative Matrix + VkBool32* shaderImageInt64Atomics; //!< Shader Image Int64 Atomics + VkBool32* sparseImageInt64Atomics; //!< Sparse Image Int64 Atomics + VkBool32* shaderModuleIdentifier; //!< Shader Module Identifier + VkBool32* shaderObject; //!< Shader Object + VkBool32* shaderReplicatedComposites; //!< Shader Replicated Composites + VkBool32* shaderTileImageColorReadAccess; //!< Shader Tile Image Color Read Access + VkBool32* shaderTileImageDepthReadAccess; //!< Shader Tile Image Depth Read Access + VkBool32* shaderTileImageStencilReadAccess; //!< Shader Tile Image Stencil Read Access + VkBool32* subpassMergeFeedback; //!< Subpass Merge Feedback + VkBool32* texelBufferAlignment; //!< Texel Buffer Alignment + VkBool32* transformFeedback; //!< Transform Feedback + VkBool32* geometryStreams; //!< Geometry Streams + VkBool32* vertexAttributeRobustness; //!< Vertex Attribute Robustness + VkBool32* vertexInputDynamicState; //!< Vertex Input Dynamic State + VkBool32* ycbcr2plane444Formats; //!< Ycbcr2plane444 Formats + VkBool32* ycbcrImageArrays; //!< Ycbcr Image Arrays + VkBool32* zeroInitializeDeviceMemory; //!< Zero Initialize Device Memory + + /// @} + + +// Methods ------------------------------------------------------------------------------------------------------------- +public: + + /// + /// \brief Features Constructor + device_features_ext() + : VkPhysicalDeviceASTCDecodeFeaturesEXT { } + , VkPhysicalDeviceAddressBindingReportFeaturesEXT { } + , VkPhysicalDeviceAttachmentFeedbackLoopDynamicStateFeaturesEXT { } + , VkPhysicalDeviceAttachmentFeedbackLoopLayoutFeaturesEXT { } + , VkPhysicalDeviceBlendOperationAdvancedFeaturesEXT { } + , VkPhysicalDeviceBorderColorSwizzleFeaturesEXT { } + , VkPhysicalDeviceBufferDeviceAddressFeaturesEXT { } + , VkPhysicalDevice4444FormatsFeaturesEXT { } + , VkPhysicalDeviceColorWriteEnableFeaturesEXT { } + , VkPhysicalDeviceConditionalRenderingFeaturesEXT { } + , VkPhysicalDeviceCustomBorderColorFeaturesEXT { } + , VkPhysicalDeviceDepthBiasControlFeaturesEXT { } + , VkPhysicalDeviceDepthClampControlFeaturesEXT { } + , VkPhysicalDeviceDepthClipControlFeaturesEXT { } + , VkPhysicalDeviceDepthClipEnableFeaturesEXT { } + , VkPhysicalDeviceDescriptorBufferFeaturesEXT { } + , VkPhysicalDeviceDeviceGeneratedCommandsFeaturesEXT { } + , VkPhysicalDeviceDeviceMemoryReportFeaturesEXT { } + , VkPhysicalDeviceDynamicRenderingUnusedAttachmentsFeaturesEXT { } + , VkPhysicalDeviceExtendedDynamicStateFeaturesEXT { } + , VkPhysicalDeviceExtendedDynamicState2FeaturesEXT { } + , VkPhysicalDeviceExtendedDynamicState3FeaturesEXT { } + , VkPhysicalDeviceFaultFeaturesEXT { } + , VkPhysicalDeviceFragmentDensityMapFeaturesEXT { } + , VkPhysicalDeviceFragmentDensityMap2FeaturesEXT { } + , VkPhysicalDeviceFragmentDensityMapOffsetFeaturesEXT { } + , VkPhysicalDeviceFragmentShaderInterlockFeaturesEXT { } + , VkPhysicalDeviceFrameBoundaryFeaturesEXT { } + , VkPhysicalDeviceGraphicsPipelineLibraryFeaturesEXT { } + , VkPhysicalDeviceImage2DViewOf3DFeaturesEXT { } + , VkPhysicalDeviceImageCompressionControlFeaturesEXT { } + , VkPhysicalDeviceImageCompressionControlSwapchainFeaturesEXT { } + , VkPhysicalDeviceImageSlicedViewOf3DFeaturesEXT { } + , VkPhysicalDeviceImageViewMinLodFeaturesEXT { } + , VkPhysicalDeviceLegacyDitheringFeaturesEXT { } + , VkPhysicalDeviceLegacyVertexAttributesFeaturesEXT { } + , VkPhysicalDeviceMapMemoryPlacedFeaturesEXT { } + , VkPhysicalDeviceMemoryPriorityFeaturesEXT { } + , VkPhysicalDeviceMeshShaderFeaturesEXT { } + , VkPhysicalDeviceMultiDrawFeaturesEXT { } + , VkPhysicalDeviceMultisampledRenderToSingleSampledFeaturesEXT { } + , VkPhysicalDeviceMutableDescriptorTypeFeaturesEXT { } + , VkPhysicalDeviceNestedCommandBufferFeaturesEXT { } + , VkPhysicalDeviceNonSeamlessCubeMapFeaturesEXT { } + , VkPhysicalDeviceOpacityMicromapFeaturesEXT { } + , VkPhysicalDevicePageableDeviceLocalMemoryFeaturesEXT { } + , VkPhysicalDevicePipelineLibraryGroupHandlesFeaturesEXT { } + , VkPhysicalDevicePipelinePropertiesFeaturesEXT { } + , VkPhysicalDevicePrimitiveTopologyListRestartFeaturesEXT { } + , VkPhysicalDevicePrimitivesGeneratedQueryFeaturesEXT { } + , VkPhysicalDeviceProvokingVertexFeaturesEXT { } + , VkPhysicalDeviceRGBA10X6FormatsFeaturesEXT { } + , VkPhysicalDeviceRasterizationOrderAttachmentAccessFeaturesEXT { } + , VkPhysicalDeviceShaderAtomicFloatFeaturesEXT { } + , VkPhysicalDeviceShaderAtomicFloat2FeaturesEXT { } + , VkPhysicalDeviceShaderFloat8FeaturesEXT { } + , VkPhysicalDeviceShaderImageAtomicInt64FeaturesEXT { } + , VkPhysicalDeviceShaderModuleIdentifierFeaturesEXT { } + , VkPhysicalDeviceShaderObjectFeaturesEXT { } + , VkPhysicalDeviceShaderReplicatedCompositesFeaturesEXT { } + , VkPhysicalDeviceShaderTileImageFeaturesEXT { } + , VkPhysicalDeviceSubpassMergeFeedbackFeaturesEXT { } + , VkPhysicalDeviceTexelBufferAlignmentFeaturesEXT { } + , VkPhysicalDeviceTransformFeedbackFeaturesEXT { } + , VkPhysicalDeviceVertexAttributeRobustnessFeaturesEXT { } + , VkPhysicalDeviceVertexInputDynamicStateFeaturesEXT { } + , VkPhysicalDeviceYcbcr2Plane444FormatsFeaturesEXT { } + , VkPhysicalDeviceYcbcrImageArraysFeaturesEXT { } + , VkPhysicalDeviceZeroInitializeDeviceMemoryFeaturesEXT { } + , decodeModeSharedExponent { nullptr } + , reportAddressBinding { nullptr } + , attachmentFeedbackLoopDynamicState { nullptr } + , attachmentFeedbackLoopLayout { nullptr } + , advancedBlendCoherentOperations { nullptr } + , borderColorSwizzle { nullptr } + , borderColorSwizzleFromImage { nullptr } + , bufferDeviceAddress { nullptr } + , bufferDeviceAddressCaptureReplay { nullptr } + , bufferDeviceAddressMultiDevice { nullptr } + , formatA4R4G4B4 { nullptr } + , formatA4B4G4R4 { nullptr } + , colorWriteEnable { nullptr } + , conditionalRendering { nullptr } + , inheritedConditionalRendering { nullptr } + , customBorderColors { nullptr } + , customBorderColorWithoutFormat { nullptr } + , depthBiasControl { nullptr } + , leastRepresentableValueForceUnormRepresentation { nullptr } + , floatRepresentation { nullptr } + , depthBiasExact { nullptr } + , depthClampControl { nullptr } + , depthClipControl { nullptr } + , depthClipEnable { nullptr } + , descriptorBuffer { nullptr } + , descriptorBufferCaptureReplay { nullptr } + , descriptorBufferImageLayoutIgnored { nullptr } + , descriptorBufferPushDescriptors { nullptr } + , deviceGeneratedCommands { nullptr } + , dynamicGeneratedPipelineLayout { nullptr } + , deviceMemoryReport { nullptr } + , dynamicRenderingUnusedAttachments { nullptr } + , extendedDynamicState { nullptr } + , extendedDynamicState2 { nullptr } + , extendedDynamicState2LogicOp { nullptr } + , extendedDynamicState2PatchControlPoints { nullptr } + , extendedDynamicState3TessellationDomainOrigin { nullptr } + , extendedDynamicState3DepthClampEnable { nullptr } + , extendedDynamicState3PolygonMode { nullptr } + , extendedDynamicState3RasterizationSamples { nullptr } + , extendedDynamicState3SampleMask { nullptr } + , extendedDynamicState3AlphaToCoverageEnable { nullptr } + , extendedDynamicState3AlphaToOneEnable { nullptr } + , extendedDynamicState3LogicOpEnable { nullptr } + , extendedDynamicState3ColorBlendEnable { nullptr } + , extendedDynamicState3ColorBlendEquation { nullptr } + , extendedDynamicState3ColorWriteMask { nullptr } + , extendedDynamicState3RasterizationStream { nullptr } + , extendedDynamicState3ConservativeRasterizationMode { nullptr } + , extendedDynamicState3ExtraPrimitiveOverestimationSize { nullptr } + , extendedDynamicState3DepthClipEnable { nullptr } + , extendedDynamicState3SampleLocationsEnable { nullptr } + , extendedDynamicState3ColorBlendAdvanced { nullptr } + , extendedDynamicState3ProvokingVertexMode { nullptr } + , extendedDynamicState3LineRasterizationMode { nullptr } + , extendedDynamicState3LineStippleEnable { nullptr } + , extendedDynamicState3DepthClipNegativeOneToOne { nullptr } + , extendedDynamicState3ViewportWScalingEnable { nullptr } + , extendedDynamicState3ViewportSwizzle { nullptr } + , extendedDynamicState3CoverageToColorEnable { nullptr } + , extendedDynamicState3CoverageToColorLocation { nullptr } + , extendedDynamicState3CoverageModulationMode { nullptr } + , extendedDynamicState3CoverageModulationTableEnable { nullptr } + , extendedDynamicState3CoverageModulationTable { nullptr } + , extendedDynamicState3CoverageReductionMode { nullptr } + , extendedDynamicState3RepresentativeFragmentTestEnable { nullptr } + , extendedDynamicState3ShadingRateImageEnable { nullptr } + , deviceFault { nullptr } + , deviceFaultVendorBinary { nullptr } + , fragmentDensityMap { nullptr } + , fragmentDensityMapDynamic { nullptr } + , fragmentDensityMapNonSubsampledImages { nullptr } + , fragmentDensityMapDeferred { nullptr } + , fragmentDensityMapOffset { nullptr } + , fragmentShaderSampleInterlock { nullptr } + , fragmentShaderPixelInterlock { nullptr } + , fragmentShaderShadingRateInterlock { nullptr } + , frameBoundary { nullptr } + , graphicsPipelineLibrary { nullptr } + , image2DViewOf3D { nullptr } + , sampler2DViewOf3D { nullptr } + , imageCompressionControl { nullptr } + , imageCompressionControlSwapchain { nullptr } + , imageSlicedViewOf3D { nullptr } + , imageMinLod { nullptr } + , legacyDithering { nullptr } + , legacyVertexAttributes { nullptr } + , memoryMapPlaced { nullptr } + , memoryMapRangePlaced { nullptr } + , memoryUnmapReserve { nullptr } + , memoryPriority { nullptr } + , taskShader { nullptr } + , meshShader { nullptr } + , multiviewMeshShader { nullptr } + , primitiveFragmentShadingRateMeshShader { nullptr } + , meshShaderQueries { nullptr } + , multiDraw { nullptr } + , multisampledRenderToSingleSampled { nullptr } + , mutableDescriptorType { nullptr } + , nestedCommandBuffer { nullptr } + , nestedCommandBufferRendering { nullptr } + , nestedCommandBufferSimultaneousUse { nullptr } + , nonSeamlessCubeMap { nullptr } + , micromap { nullptr } + , micromapCaptureReplay { nullptr } + , micromapHostCommands { nullptr } + , pageableDeviceLocalMemory { nullptr } + , pipelineLibraryGroupHandles { nullptr } + , pipelinePropertiesIdentifier { nullptr } + , primitiveTopologyListRestart { nullptr } + , primitiveTopologyPatchListRestart { nullptr } + , primitivesGeneratedQuery { nullptr } + , primitivesGeneratedQueryWithRasterizerDiscard { nullptr } + , primitivesGeneratedQueryWithNonZeroStreams { nullptr } + , provokingVertexLast { nullptr } + , transformFeedbackPreservesProvokingVertex { nullptr } + , formatRgba10x6WithoutYCbCrSampler { nullptr } + , rasterizationOrderColorAttachmentAccess { nullptr } + , rasterizationOrderDepthAttachmentAccess { nullptr } + , rasterizationOrderStencilAttachmentAccess { nullptr } + , shaderBufferFloat32Atomics { nullptr } + , shaderBufferFloat32AtomicAdd { nullptr } + , shaderBufferFloat64Atomics { nullptr } + , shaderBufferFloat64AtomicAdd { nullptr } + , shaderSharedFloat32Atomics { nullptr } + , shaderSharedFloat32AtomicAdd { nullptr } + , shaderSharedFloat64Atomics { nullptr } + , shaderSharedFloat64AtomicAdd { nullptr } + , shaderImageFloat32Atomics { nullptr } + , shaderImageFloat32AtomicAdd { nullptr } + , sparseImageFloat32Atomics { nullptr } + , sparseImageFloat32AtomicAdd { nullptr } + , shaderBufferFloat16Atomics { nullptr } + , shaderBufferFloat16AtomicAdd { nullptr } + , shaderBufferFloat16AtomicMinMax { nullptr } + , shaderBufferFloat32AtomicMinMax { nullptr } + , shaderBufferFloat64AtomicMinMax { nullptr } + , shaderSharedFloat16Atomics { nullptr } + , shaderSharedFloat16AtomicAdd { nullptr } + , shaderSharedFloat16AtomicMinMax { nullptr } + , shaderSharedFloat32AtomicMinMax { nullptr } + , shaderSharedFloat64AtomicMinMax { nullptr } + , shaderImageFloat32AtomicMinMax { nullptr } + , sparseImageFloat32AtomicMinMax { nullptr } + , shaderFloat8 { nullptr } + , shaderFloat8CooperativeMatrix { nullptr } + , shaderImageInt64Atomics { nullptr } + , sparseImageInt64Atomics { nullptr } + , shaderModuleIdentifier { nullptr } + , shaderObject { nullptr } + , shaderReplicatedComposites { nullptr } + , shaderTileImageColorReadAccess { nullptr } + , shaderTileImageDepthReadAccess { nullptr } + , shaderTileImageStencilReadAccess { nullptr } + , subpassMergeFeedback { nullptr } + , texelBufferAlignment { nullptr } + , transformFeedback { nullptr } + , geometryStreams { nullptr } + , vertexAttributeRobustness { nullptr } + , vertexInputDynamicState { nullptr } + , ycbcr2plane444Formats { nullptr } + , ycbcrImageArrays { nullptr } + , zeroInitializeDeviceMemory { nullptr } { + + _clear(); + _link(); + } + + + /// + /// \brief Copy Constructor + /// \param features The features structure to copy + device_features_ext(const device_features_ext& features) + : VkPhysicalDeviceASTCDecodeFeaturesEXT { features } + , VkPhysicalDeviceAddressBindingReportFeaturesEXT { features } + , VkPhysicalDeviceAttachmentFeedbackLoopDynamicStateFeaturesEXT { features } + , VkPhysicalDeviceAttachmentFeedbackLoopLayoutFeaturesEXT { features } + , VkPhysicalDeviceBlendOperationAdvancedFeaturesEXT { features } + , VkPhysicalDeviceBorderColorSwizzleFeaturesEXT { features } + , VkPhysicalDeviceBufferDeviceAddressFeaturesEXT { features } + , VkPhysicalDevice4444FormatsFeaturesEXT { features } + , VkPhysicalDeviceColorWriteEnableFeaturesEXT { features } + , VkPhysicalDeviceConditionalRenderingFeaturesEXT { features } + , VkPhysicalDeviceCustomBorderColorFeaturesEXT { features } + , VkPhysicalDeviceDepthBiasControlFeaturesEXT { features } + , VkPhysicalDeviceDepthClampControlFeaturesEXT { features } + , VkPhysicalDeviceDepthClipControlFeaturesEXT { features } + , VkPhysicalDeviceDepthClipEnableFeaturesEXT { features } + , VkPhysicalDeviceDescriptorBufferFeaturesEXT { features } + , VkPhysicalDeviceDeviceGeneratedCommandsFeaturesEXT { features } + , VkPhysicalDeviceDeviceMemoryReportFeaturesEXT { features } + , VkPhysicalDeviceDynamicRenderingUnusedAttachmentsFeaturesEXT { features } + , VkPhysicalDeviceExtendedDynamicStateFeaturesEXT { features } + , VkPhysicalDeviceExtendedDynamicState2FeaturesEXT { features } + , VkPhysicalDeviceExtendedDynamicState3FeaturesEXT { features } + , VkPhysicalDeviceFaultFeaturesEXT { features } + , VkPhysicalDeviceFragmentDensityMapFeaturesEXT { features } + , VkPhysicalDeviceFragmentDensityMap2FeaturesEXT { features } + , VkPhysicalDeviceFragmentDensityMapOffsetFeaturesEXT { features } + , VkPhysicalDeviceFragmentShaderInterlockFeaturesEXT { features } + , VkPhysicalDeviceFrameBoundaryFeaturesEXT { features } + , VkPhysicalDeviceGraphicsPipelineLibraryFeaturesEXT { features } + , VkPhysicalDeviceImage2DViewOf3DFeaturesEXT { features } + , VkPhysicalDeviceImageCompressionControlFeaturesEXT { features } + , VkPhysicalDeviceImageCompressionControlSwapchainFeaturesEXT { features } + , VkPhysicalDeviceImageSlicedViewOf3DFeaturesEXT { features } + , VkPhysicalDeviceImageViewMinLodFeaturesEXT { features } + , VkPhysicalDeviceLegacyDitheringFeaturesEXT { features } + , VkPhysicalDeviceLegacyVertexAttributesFeaturesEXT { features } + , VkPhysicalDeviceMapMemoryPlacedFeaturesEXT { features } + , VkPhysicalDeviceMemoryPriorityFeaturesEXT { features } + , VkPhysicalDeviceMeshShaderFeaturesEXT { features } + , VkPhysicalDeviceMultiDrawFeaturesEXT { features } + , VkPhysicalDeviceMultisampledRenderToSingleSampledFeaturesEXT { features } + , VkPhysicalDeviceMutableDescriptorTypeFeaturesEXT { features } + , VkPhysicalDeviceNestedCommandBufferFeaturesEXT { features } + , VkPhysicalDeviceNonSeamlessCubeMapFeaturesEXT { features } + , VkPhysicalDeviceOpacityMicromapFeaturesEXT { features } + , VkPhysicalDevicePageableDeviceLocalMemoryFeaturesEXT { features } + , VkPhysicalDevicePipelineLibraryGroupHandlesFeaturesEXT { features } + , VkPhysicalDevicePipelinePropertiesFeaturesEXT { features } + , VkPhysicalDevicePrimitiveTopologyListRestartFeaturesEXT { features } + , VkPhysicalDevicePrimitivesGeneratedQueryFeaturesEXT { features } + , VkPhysicalDeviceProvokingVertexFeaturesEXT { features } + , VkPhysicalDeviceRGBA10X6FormatsFeaturesEXT { features } + , VkPhysicalDeviceRasterizationOrderAttachmentAccessFeaturesEXT { features } + , VkPhysicalDeviceShaderAtomicFloatFeaturesEXT { features } + , VkPhysicalDeviceShaderAtomicFloat2FeaturesEXT { features } + , VkPhysicalDeviceShaderFloat8FeaturesEXT { features } + , VkPhysicalDeviceShaderImageAtomicInt64FeaturesEXT { features } + , VkPhysicalDeviceShaderModuleIdentifierFeaturesEXT { features } + , VkPhysicalDeviceShaderObjectFeaturesEXT { features } + , VkPhysicalDeviceShaderReplicatedCompositesFeaturesEXT { features } + , VkPhysicalDeviceShaderTileImageFeaturesEXT { features } + , VkPhysicalDeviceSubpassMergeFeedbackFeaturesEXT { features } + , VkPhysicalDeviceTexelBufferAlignmentFeaturesEXT { features } + , VkPhysicalDeviceTransformFeedbackFeaturesEXT { features } + , VkPhysicalDeviceVertexAttributeRobustnessFeaturesEXT { features } + , VkPhysicalDeviceVertexInputDynamicStateFeaturesEXT { features } + , VkPhysicalDeviceYcbcr2Plane444FormatsFeaturesEXT { features } + , VkPhysicalDeviceYcbcrImageArraysFeaturesEXT { features } + , VkPhysicalDeviceZeroInitializeDeviceMemoryFeaturesEXT { features } + , decodeModeSharedExponent { nullptr } + , reportAddressBinding { nullptr } + , attachmentFeedbackLoopDynamicState { nullptr } + , attachmentFeedbackLoopLayout { nullptr } + , advancedBlendCoherentOperations { nullptr } + , borderColorSwizzle { nullptr } + , borderColorSwizzleFromImage { nullptr } + , bufferDeviceAddress { nullptr } + , bufferDeviceAddressCaptureReplay { nullptr } + , bufferDeviceAddressMultiDevice { nullptr } + , formatA4R4G4B4 { nullptr } + , formatA4B4G4R4 { nullptr } + , colorWriteEnable { nullptr } + , conditionalRendering { nullptr } + , inheritedConditionalRendering { nullptr } + , customBorderColors { nullptr } + , customBorderColorWithoutFormat { nullptr } + , depthBiasControl { nullptr } + , leastRepresentableValueForceUnormRepresentation { nullptr } + , floatRepresentation { nullptr } + , depthBiasExact { nullptr } + , depthClampControl { nullptr } + , depthClipControl { nullptr } + , depthClipEnable { nullptr } + , descriptorBuffer { nullptr } + , descriptorBufferCaptureReplay { nullptr } + , descriptorBufferImageLayoutIgnored { nullptr } + , descriptorBufferPushDescriptors { nullptr } + , deviceGeneratedCommands { nullptr } + , dynamicGeneratedPipelineLayout { nullptr } + , deviceMemoryReport { nullptr } + , dynamicRenderingUnusedAttachments { nullptr } + , extendedDynamicState { nullptr } + , extendedDynamicState2 { nullptr } + , extendedDynamicState2LogicOp { nullptr } + , extendedDynamicState2PatchControlPoints { nullptr } + , extendedDynamicState3TessellationDomainOrigin { nullptr } + , extendedDynamicState3DepthClampEnable { nullptr } + , extendedDynamicState3PolygonMode { nullptr } + , extendedDynamicState3RasterizationSamples { nullptr } + , extendedDynamicState3SampleMask { nullptr } + , extendedDynamicState3AlphaToCoverageEnable { nullptr } + , extendedDynamicState3AlphaToOneEnable { nullptr } + , extendedDynamicState3LogicOpEnable { nullptr } + , extendedDynamicState3ColorBlendEnable { nullptr } + , extendedDynamicState3ColorBlendEquation { nullptr } + , extendedDynamicState3ColorWriteMask { nullptr } + , extendedDynamicState3RasterizationStream { nullptr } + , extendedDynamicState3ConservativeRasterizationMode { nullptr } + , extendedDynamicState3ExtraPrimitiveOverestimationSize { nullptr } + , extendedDynamicState3DepthClipEnable { nullptr } + , extendedDynamicState3SampleLocationsEnable { nullptr } + , extendedDynamicState3ColorBlendAdvanced { nullptr } + , extendedDynamicState3ProvokingVertexMode { nullptr } + , extendedDynamicState3LineRasterizationMode { nullptr } + , extendedDynamicState3LineStippleEnable { nullptr } + , extendedDynamicState3DepthClipNegativeOneToOne { nullptr } + , extendedDynamicState3ViewportWScalingEnable { nullptr } + , extendedDynamicState3ViewportSwizzle { nullptr } + , extendedDynamicState3CoverageToColorEnable { nullptr } + , extendedDynamicState3CoverageToColorLocation { nullptr } + , extendedDynamicState3CoverageModulationMode { nullptr } + , extendedDynamicState3CoverageModulationTableEnable { nullptr } + , extendedDynamicState3CoverageModulationTable { nullptr } + , extendedDynamicState3CoverageReductionMode { nullptr } + , extendedDynamicState3RepresentativeFragmentTestEnable { nullptr } + , extendedDynamicState3ShadingRateImageEnable { nullptr } + , deviceFault { nullptr } + , deviceFaultVendorBinary { nullptr } + , fragmentDensityMap { nullptr } + , fragmentDensityMapDynamic { nullptr } + , fragmentDensityMapNonSubsampledImages { nullptr } + , fragmentDensityMapDeferred { nullptr } + , fragmentDensityMapOffset { nullptr } + , fragmentShaderSampleInterlock { nullptr } + , fragmentShaderPixelInterlock { nullptr } + , fragmentShaderShadingRateInterlock { nullptr } + , frameBoundary { nullptr } + , graphicsPipelineLibrary { nullptr } + , image2DViewOf3D { nullptr } + , sampler2DViewOf3D { nullptr } + , imageCompressionControl { nullptr } + , imageCompressionControlSwapchain { nullptr } + , imageSlicedViewOf3D { nullptr } + , imageMinLod { nullptr } + , legacyDithering { nullptr } + , legacyVertexAttributes { nullptr } + , memoryMapPlaced { nullptr } + , memoryMapRangePlaced { nullptr } + , memoryUnmapReserve { nullptr } + , memoryPriority { nullptr } + , taskShader { nullptr } + , meshShader { nullptr } + , multiviewMeshShader { nullptr } + , primitiveFragmentShadingRateMeshShader { nullptr } + , meshShaderQueries { nullptr } + , multiDraw { nullptr } + , multisampledRenderToSingleSampled { nullptr } + , mutableDescriptorType { nullptr } + , nestedCommandBuffer { nullptr } + , nestedCommandBufferRendering { nullptr } + , nestedCommandBufferSimultaneousUse { nullptr } + , nonSeamlessCubeMap { nullptr } + , micromap { nullptr } + , micromapCaptureReplay { nullptr } + , micromapHostCommands { nullptr } + , pageableDeviceLocalMemory { nullptr } + , pipelineLibraryGroupHandles { nullptr } + , pipelinePropertiesIdentifier { nullptr } + , primitiveTopologyListRestart { nullptr } + , primitiveTopologyPatchListRestart { nullptr } + , primitivesGeneratedQuery { nullptr } + , primitivesGeneratedQueryWithRasterizerDiscard { nullptr } + , primitivesGeneratedQueryWithNonZeroStreams { nullptr } + , provokingVertexLast { nullptr } + , transformFeedbackPreservesProvokingVertex { nullptr } + , formatRgba10x6WithoutYCbCrSampler { nullptr } + , rasterizationOrderColorAttachmentAccess { nullptr } + , rasterizationOrderDepthAttachmentAccess { nullptr } + , rasterizationOrderStencilAttachmentAccess { nullptr } + , shaderBufferFloat32Atomics { nullptr } + , shaderBufferFloat32AtomicAdd { nullptr } + , shaderBufferFloat64Atomics { nullptr } + , shaderBufferFloat64AtomicAdd { nullptr } + , shaderSharedFloat32Atomics { nullptr } + , shaderSharedFloat32AtomicAdd { nullptr } + , shaderSharedFloat64Atomics { nullptr } + , shaderSharedFloat64AtomicAdd { nullptr } + , shaderImageFloat32Atomics { nullptr } + , shaderImageFloat32AtomicAdd { nullptr } + , sparseImageFloat32Atomics { nullptr } + , sparseImageFloat32AtomicAdd { nullptr } + , shaderBufferFloat16Atomics { nullptr } + , shaderBufferFloat16AtomicAdd { nullptr } + , shaderBufferFloat16AtomicMinMax { nullptr } + , shaderBufferFloat32AtomicMinMax { nullptr } + , shaderBufferFloat64AtomicMinMax { nullptr } + , shaderSharedFloat16Atomics { nullptr } + , shaderSharedFloat16AtomicAdd { nullptr } + , shaderSharedFloat16AtomicMinMax { nullptr } + , shaderSharedFloat32AtomicMinMax { nullptr } + , shaderSharedFloat64AtomicMinMax { nullptr } + , shaderImageFloat32AtomicMinMax { nullptr } + , sparseImageFloat32AtomicMinMax { nullptr } + , shaderFloat8 { nullptr } + , shaderFloat8CooperativeMatrix { nullptr } + , shaderImageInt64Atomics { nullptr } + , sparseImageInt64Atomics { nullptr } + , shaderModuleIdentifier { nullptr } + , shaderObject { nullptr } + , shaderReplicatedComposites { nullptr } + , shaderTileImageColorReadAccess { nullptr } + , shaderTileImageDepthReadAccess { nullptr } + , shaderTileImageStencilReadAccess { nullptr } + , subpassMergeFeedback { nullptr } + , texelBufferAlignment { nullptr } + , transformFeedback { nullptr } + , geometryStreams { nullptr } + , vertexAttributeRobustness { nullptr } + , vertexInputDynamicState { nullptr } + , ycbcr2plane444Formats { nullptr } + , ycbcrImageArrays { nullptr } + , zeroInitializeDeviceMemory { nullptr } { + + _link(); + } + + /// + /// \brief Copy Assignment + /// \param features The features to copy + /// \returns A reference to \emph{this} + device_features_ext& operator=(const device_features_ext& features) { + + // Copy Data + VkPhysicalDeviceASTCDecodeFeaturesEXT::operator=(features); + VkPhysicalDeviceAddressBindingReportFeaturesEXT::operator=(features); + VkPhysicalDeviceAttachmentFeedbackLoopDynamicStateFeaturesEXT::operator=(features); + VkPhysicalDeviceAttachmentFeedbackLoopLayoutFeaturesEXT::operator=(features); + VkPhysicalDeviceBlendOperationAdvancedFeaturesEXT::operator=(features); + VkPhysicalDeviceBorderColorSwizzleFeaturesEXT::operator=(features); + VkPhysicalDeviceBufferDeviceAddressFeaturesEXT::operator=(features); + VkPhysicalDevice4444FormatsFeaturesEXT::operator=(features); + VkPhysicalDeviceColorWriteEnableFeaturesEXT::operator=(features); + VkPhysicalDeviceConditionalRenderingFeaturesEXT::operator=(features); + VkPhysicalDeviceCustomBorderColorFeaturesEXT::operator=(features); + VkPhysicalDeviceDepthBiasControlFeaturesEXT::operator=(features); + VkPhysicalDeviceDepthClampControlFeaturesEXT::operator=(features); + VkPhysicalDeviceDepthClipControlFeaturesEXT::operator=(features); + VkPhysicalDeviceDepthClipEnableFeaturesEXT::operator=(features); + VkPhysicalDeviceDescriptorBufferFeaturesEXT::operator=(features); + VkPhysicalDeviceDeviceGeneratedCommandsFeaturesEXT::operator=(features); + VkPhysicalDeviceDeviceMemoryReportFeaturesEXT::operator=(features); + VkPhysicalDeviceDynamicRenderingUnusedAttachmentsFeaturesEXT::operator=(features); + VkPhysicalDeviceExtendedDynamicStateFeaturesEXT::operator=(features); + VkPhysicalDeviceExtendedDynamicState2FeaturesEXT::operator=(features); + VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::operator=(features); + VkPhysicalDeviceFaultFeaturesEXT::operator=(features); + VkPhysicalDeviceFragmentDensityMapFeaturesEXT::operator=(features); + VkPhysicalDeviceFragmentDensityMap2FeaturesEXT::operator=(features); + VkPhysicalDeviceFragmentDensityMapOffsetFeaturesEXT::operator=(features); + VkPhysicalDeviceFragmentShaderInterlockFeaturesEXT::operator=(features); + VkPhysicalDeviceFrameBoundaryFeaturesEXT::operator=(features); + VkPhysicalDeviceGraphicsPipelineLibraryFeaturesEXT::operator=(features); + VkPhysicalDeviceImage2DViewOf3DFeaturesEXT::operator=(features); + VkPhysicalDeviceImageCompressionControlFeaturesEXT::operator=(features); + VkPhysicalDeviceImageCompressionControlSwapchainFeaturesEXT::operator=(features); + VkPhysicalDeviceImageSlicedViewOf3DFeaturesEXT::operator=(features); + VkPhysicalDeviceImageViewMinLodFeaturesEXT::operator=(features); + VkPhysicalDeviceLegacyDitheringFeaturesEXT::operator=(features); + VkPhysicalDeviceLegacyVertexAttributesFeaturesEXT::operator=(features); + VkPhysicalDeviceMapMemoryPlacedFeaturesEXT::operator=(features); + VkPhysicalDeviceMemoryPriorityFeaturesEXT::operator=(features); + VkPhysicalDeviceMeshShaderFeaturesEXT::operator=(features); + VkPhysicalDeviceMultiDrawFeaturesEXT::operator=(features); + VkPhysicalDeviceMultisampledRenderToSingleSampledFeaturesEXT::operator=(features); + VkPhysicalDeviceMutableDescriptorTypeFeaturesEXT::operator=(features); + VkPhysicalDeviceNestedCommandBufferFeaturesEXT::operator=(features); + VkPhysicalDeviceNonSeamlessCubeMapFeaturesEXT::operator=(features); + VkPhysicalDeviceOpacityMicromapFeaturesEXT::operator=(features); + VkPhysicalDevicePageableDeviceLocalMemoryFeaturesEXT::operator=(features); + VkPhysicalDevicePipelineLibraryGroupHandlesFeaturesEXT::operator=(features); + VkPhysicalDevicePipelinePropertiesFeaturesEXT::operator=(features); + VkPhysicalDevicePrimitiveTopologyListRestartFeaturesEXT::operator=(features); + VkPhysicalDevicePrimitivesGeneratedQueryFeaturesEXT::operator=(features); + VkPhysicalDeviceProvokingVertexFeaturesEXT::operator=(features); + VkPhysicalDeviceRGBA10X6FormatsFeaturesEXT::operator=(features); + VkPhysicalDeviceRasterizationOrderAttachmentAccessFeaturesEXT::operator=(features); + VkPhysicalDeviceShaderAtomicFloatFeaturesEXT::operator=(features); + VkPhysicalDeviceShaderAtomicFloat2FeaturesEXT::operator=(features); + VkPhysicalDeviceShaderFloat8FeaturesEXT::operator=(features); + VkPhysicalDeviceShaderImageAtomicInt64FeaturesEXT::operator=(features); + VkPhysicalDeviceShaderModuleIdentifierFeaturesEXT::operator=(features); + VkPhysicalDeviceShaderObjectFeaturesEXT::operator=(features); + VkPhysicalDeviceShaderReplicatedCompositesFeaturesEXT::operator=(features); + VkPhysicalDeviceShaderTileImageFeaturesEXT::operator=(features); + VkPhysicalDeviceSubpassMergeFeedbackFeaturesEXT::operator=(features); + VkPhysicalDeviceTexelBufferAlignmentFeaturesEXT::operator=(features); + VkPhysicalDeviceTransformFeedbackFeaturesEXT::operator=(features); + VkPhysicalDeviceVertexAttributeRobustnessFeaturesEXT::operator=(features); + VkPhysicalDeviceVertexInputDynamicStateFeaturesEXT::operator=(features); + VkPhysicalDeviceYcbcr2Plane444FormatsFeaturesEXT::operator=(features); + VkPhysicalDeviceYcbcrImageArraysFeaturesEXT::operator=(features); + VkPhysicalDeviceZeroInitializeDeviceMemoryFeaturesEXT::operator=(features); + + _link(); + + return *this; + } + + + /// + /// \brief Chain an extension structure + /// \param next + void chain(void* next) { + VkPhysicalDeviceZeroInitializeDeviceMemoryFeaturesEXT::pNext = next; + } + + /// + /// \brief Implicit casting for chaining + operator void*() { + return static_cast(this); + } + + +// Helpers ------------------------------------------------------------------------------------------------------------- +private: + + void _clear() { + + // Clear out the struct + fennec::memset(this, 0, sizeof(*this)); + + + // Set the structure types + VkPhysicalDeviceASTCDecodeFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_ASTC_DECODE_FEATURES_EXT; + VkPhysicalDeviceAddressBindingReportFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_ADDRESS_BINDING_REPORT_FEATURES_EXT; + VkPhysicalDeviceAttachmentFeedbackLoopDynamicStateFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_ATTACHMENT_FEEDBACK_LOOP_DYNAMIC_STATE_FEATURES_EXT; + VkPhysicalDeviceAttachmentFeedbackLoopLayoutFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_ATTACHMENT_FEEDBACK_LOOP_LAYOUT_FEATURES_EXT; + VkPhysicalDeviceBlendOperationAdvancedFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_BLEND_OPERATION_ADVANCED_FEATURES_EXT; + VkPhysicalDeviceBorderColorSwizzleFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_BORDER_COLOR_SWIZZLE_FEATURES_EXT; + VkPhysicalDeviceBorderColorSwizzleFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_BORDER_COLOR_SWIZZLE_FEATURES_EXT; + VkPhysicalDeviceBufferDeviceAddressFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_BUFFER_DEVICE_ADDRESS_FEATURES_EXT; + VkPhysicalDeviceBufferDeviceAddressFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_BUFFER_DEVICE_ADDRESS_FEATURES_EXT; + VkPhysicalDeviceBufferDeviceAddressFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_BUFFER_DEVICE_ADDRESS_FEATURES_EXT; + VkPhysicalDevice4444FormatsFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_4444_FORMATS_FEATURES_EXT; + VkPhysicalDevice4444FormatsFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_4444_FORMATS_FEATURES_EXT; + VkPhysicalDeviceColorWriteEnableFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_COLOR_WRITE_ENABLE_FEATURES_EXT; + VkPhysicalDeviceConditionalRenderingFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_CONDITIONAL_RENDERING_FEATURES_EXT; + VkPhysicalDeviceConditionalRenderingFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_CONDITIONAL_RENDERING_FEATURES_EXT; + VkPhysicalDeviceCustomBorderColorFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_CUSTOM_BORDER_COLOR_FEATURES_EXT; + VkPhysicalDeviceCustomBorderColorFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_CUSTOM_BORDER_COLOR_FEATURES_EXT; + VkPhysicalDeviceDepthBiasControlFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_DEPTH_BIAS_CONTROL_FEATURES_EXT; + VkPhysicalDeviceDepthBiasControlFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_DEPTH_BIAS_CONTROL_FEATURES_EXT; + VkPhysicalDeviceDepthBiasControlFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_DEPTH_BIAS_CONTROL_FEATURES_EXT; + VkPhysicalDeviceDepthBiasControlFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_DEPTH_BIAS_CONTROL_FEATURES_EXT; + VkPhysicalDeviceDepthClampControlFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_DEPTH_CLAMP_CONTROL_FEATURES_EXT; + VkPhysicalDeviceDepthClipControlFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_DEPTH_CLIP_CONTROL_FEATURES_EXT; + VkPhysicalDeviceDepthClipEnableFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_DEPTH_CLIP_ENABLE_FEATURES_EXT; + VkPhysicalDeviceDescriptorBufferFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_DESCRIPTOR_BUFFER_FEATURES_EXT; + VkPhysicalDeviceDescriptorBufferFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_DESCRIPTOR_BUFFER_FEATURES_EXT; + VkPhysicalDeviceDescriptorBufferFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_DESCRIPTOR_BUFFER_FEATURES_EXT; + VkPhysicalDeviceDescriptorBufferFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_DESCRIPTOR_BUFFER_FEATURES_EXT; + VkPhysicalDeviceDeviceGeneratedCommandsFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_DEVICE_GENERATED_COMMANDS_FEATURES_EXT; + VkPhysicalDeviceDeviceGeneratedCommandsFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_DEVICE_GENERATED_COMMANDS_FEATURES_EXT; + VkPhysicalDeviceDeviceMemoryReportFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_DEVICE_MEMORY_REPORT_FEATURES_EXT; + VkPhysicalDeviceDynamicRenderingUnusedAttachmentsFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_DYNAMIC_RENDERING_UNUSED_ATTACHMENTS_FEATURES_EXT; + VkPhysicalDeviceExtendedDynamicStateFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_EXTENDED_DYNAMIC_STATE_FEATURES_EXT; + VkPhysicalDeviceExtendedDynamicState2FeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_EXTENDED_DYNAMIC_STATE_2_FEATURES_EXT; + VkPhysicalDeviceExtendedDynamicState2FeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_EXTENDED_DYNAMIC_STATE_2_FEATURES_EXT; + VkPhysicalDeviceExtendedDynamicState2FeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_EXTENDED_DYNAMIC_STATE_2_FEATURES_EXT; + VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_EXTENDED_DYNAMIC_STATE_3_FEATURES_EXT; + VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_EXTENDED_DYNAMIC_STATE_3_FEATURES_EXT; + VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_EXTENDED_DYNAMIC_STATE_3_FEATURES_EXT; + VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_EXTENDED_DYNAMIC_STATE_3_FEATURES_EXT; + VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_EXTENDED_DYNAMIC_STATE_3_FEATURES_EXT; + VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_EXTENDED_DYNAMIC_STATE_3_FEATURES_EXT; + VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_EXTENDED_DYNAMIC_STATE_3_FEATURES_EXT; + VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_EXTENDED_DYNAMIC_STATE_3_FEATURES_EXT; + VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_EXTENDED_DYNAMIC_STATE_3_FEATURES_EXT; + VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_EXTENDED_DYNAMIC_STATE_3_FEATURES_EXT; + VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_EXTENDED_DYNAMIC_STATE_3_FEATURES_EXT; + VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_EXTENDED_DYNAMIC_STATE_3_FEATURES_EXT; + VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_EXTENDED_DYNAMIC_STATE_3_FEATURES_EXT; + VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_EXTENDED_DYNAMIC_STATE_3_FEATURES_EXT; + VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_EXTENDED_DYNAMIC_STATE_3_FEATURES_EXT; + VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_EXTENDED_DYNAMIC_STATE_3_FEATURES_EXT; + VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_EXTENDED_DYNAMIC_STATE_3_FEATURES_EXT; + VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_EXTENDED_DYNAMIC_STATE_3_FEATURES_EXT; + VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_EXTENDED_DYNAMIC_STATE_3_FEATURES_EXT; + VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_EXTENDED_DYNAMIC_STATE_3_FEATURES_EXT; + VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_EXTENDED_DYNAMIC_STATE_3_FEATURES_EXT; + VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_EXTENDED_DYNAMIC_STATE_3_FEATURES_EXT; + VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_EXTENDED_DYNAMIC_STATE_3_FEATURES_EXT; + VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_EXTENDED_DYNAMIC_STATE_3_FEATURES_EXT; + VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_EXTENDED_DYNAMIC_STATE_3_FEATURES_EXT; + VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_EXTENDED_DYNAMIC_STATE_3_FEATURES_EXT; + VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_EXTENDED_DYNAMIC_STATE_3_FEATURES_EXT; + VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_EXTENDED_DYNAMIC_STATE_3_FEATURES_EXT; + VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_EXTENDED_DYNAMIC_STATE_3_FEATURES_EXT; + VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_EXTENDED_DYNAMIC_STATE_3_FEATURES_EXT; + VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_EXTENDED_DYNAMIC_STATE_3_FEATURES_EXT; + VkPhysicalDeviceFaultFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_FAULT_FEATURES_EXT; + VkPhysicalDeviceFaultFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_FAULT_FEATURES_EXT; + VkPhysicalDeviceFragmentDensityMapFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_FRAGMENT_DENSITY_MAP_FEATURES_EXT; + VkPhysicalDeviceFragmentDensityMapFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_FRAGMENT_DENSITY_MAP_FEATURES_EXT; + VkPhysicalDeviceFragmentDensityMapFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_FRAGMENT_DENSITY_MAP_FEATURES_EXT; + VkPhysicalDeviceFragmentDensityMap2FeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_FRAGMENT_DENSITY_MAP_2_FEATURES_EXT; + VkPhysicalDeviceFragmentDensityMapOffsetFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_FRAGMENT_DENSITY_MAP_OFFSET_FEATURES_EXT; + VkPhysicalDeviceFragmentShaderInterlockFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_FRAGMENT_SHADER_INTERLOCK_FEATURES_EXT; + VkPhysicalDeviceFragmentShaderInterlockFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_FRAGMENT_SHADER_INTERLOCK_FEATURES_EXT; + VkPhysicalDeviceFragmentShaderInterlockFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_FRAGMENT_SHADER_INTERLOCK_FEATURES_EXT; + VkPhysicalDeviceFrameBoundaryFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_FRAME_BOUNDARY_FEATURES_EXT; + VkPhysicalDeviceGraphicsPipelineLibraryFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_GRAPHICS_PIPELINE_LIBRARY_FEATURES_EXT; + VkPhysicalDeviceImage2DViewOf3DFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_IMAGE_2D_VIEW_OF_3D_FEATURES_EXT; + VkPhysicalDeviceImage2DViewOf3DFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_IMAGE_2D_VIEW_OF_3D_FEATURES_EXT; + VkPhysicalDeviceImageCompressionControlFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_IMAGE_COMPRESSION_CONTROL_FEATURES_EXT; + VkPhysicalDeviceImageCompressionControlSwapchainFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_IMAGE_COMPRESSION_CONTROL_SWAPCHAIN_FEATURES_EXT; + VkPhysicalDeviceImageSlicedViewOf3DFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_IMAGE_SLICED_VIEW_OF_3D_FEATURES_EXT; + VkPhysicalDeviceImageViewMinLodFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_IMAGE_VIEW_MIN_LOD_FEATURES_EXT; + VkPhysicalDeviceLegacyDitheringFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_LEGACY_DITHERING_FEATURES_EXT; + VkPhysicalDeviceLegacyVertexAttributesFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_LEGACY_VERTEX_ATTRIBUTES_FEATURES_EXT; + VkPhysicalDeviceMapMemoryPlacedFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_MAP_MEMORY_PLACED_FEATURES_EXT; + VkPhysicalDeviceMapMemoryPlacedFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_MAP_MEMORY_PLACED_FEATURES_EXT; + VkPhysicalDeviceMapMemoryPlacedFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_MAP_MEMORY_PLACED_FEATURES_EXT; + VkPhysicalDeviceMemoryPriorityFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_MEMORY_PRIORITY_FEATURES_EXT; + VkPhysicalDeviceMeshShaderFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_MESH_SHADER_FEATURES_EXT; + VkPhysicalDeviceMeshShaderFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_MESH_SHADER_FEATURES_EXT; + VkPhysicalDeviceMeshShaderFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_MESH_SHADER_FEATURES_EXT; + VkPhysicalDeviceMeshShaderFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_MESH_SHADER_FEATURES_EXT; + VkPhysicalDeviceMeshShaderFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_MESH_SHADER_FEATURES_EXT; + VkPhysicalDeviceMultiDrawFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_MULTI_DRAW_FEATURES_EXT; + VkPhysicalDeviceMultisampledRenderToSingleSampledFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_MULTISAMPLED_RENDER_TO_SINGLE_SAMPLED_FEATURES_EXT; + VkPhysicalDeviceMutableDescriptorTypeFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_MUTABLE_DESCRIPTOR_TYPE_FEATURES_EXT; + VkPhysicalDeviceNestedCommandBufferFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_NESTED_COMMAND_BUFFER_FEATURES_EXT; + VkPhysicalDeviceNestedCommandBufferFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_NESTED_COMMAND_BUFFER_FEATURES_EXT; + VkPhysicalDeviceNestedCommandBufferFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_NESTED_COMMAND_BUFFER_FEATURES_EXT; + VkPhysicalDeviceNonSeamlessCubeMapFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_NON_SEAMLESS_CUBE_MAP_FEATURES_EXT; + VkPhysicalDeviceOpacityMicromapFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_OPACITY_MICROMAP_FEATURES_EXT; + VkPhysicalDeviceOpacityMicromapFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_OPACITY_MICROMAP_FEATURES_EXT; + VkPhysicalDeviceOpacityMicromapFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_OPACITY_MICROMAP_FEATURES_EXT; + VkPhysicalDevicePageableDeviceLocalMemoryFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_PAGEABLE_DEVICE_LOCAL_MEMORY_FEATURES_EXT; + VkPhysicalDevicePipelineLibraryGroupHandlesFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_PIPELINE_LIBRARY_GROUP_HANDLES_FEATURES_EXT; + VkPhysicalDevicePipelinePropertiesFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_PIPELINE_PROPERTIES_FEATURES_EXT; + VkPhysicalDevicePrimitiveTopologyListRestartFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_PRIMITIVE_TOPOLOGY_LIST_RESTART_FEATURES_EXT; + VkPhysicalDevicePrimitiveTopologyListRestartFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_PRIMITIVE_TOPOLOGY_LIST_RESTART_FEATURES_EXT; + VkPhysicalDevicePrimitivesGeneratedQueryFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_PRIMITIVES_GENERATED_QUERY_FEATURES_EXT; + VkPhysicalDevicePrimitivesGeneratedQueryFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_PRIMITIVES_GENERATED_QUERY_FEATURES_EXT; + VkPhysicalDevicePrimitivesGeneratedQueryFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_PRIMITIVES_GENERATED_QUERY_FEATURES_EXT; + VkPhysicalDeviceProvokingVertexFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_PROVOKING_VERTEX_FEATURES_EXT; + VkPhysicalDeviceProvokingVertexFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_PROVOKING_VERTEX_FEATURES_EXT; + VkPhysicalDeviceRGBA10X6FormatsFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_RGBA10X6_FORMATS_FEATURES_EXT; + VkPhysicalDeviceRasterizationOrderAttachmentAccessFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_RASTERIZATION_ORDER_ATTACHMENT_ACCESS_FEATURES_EXT; + VkPhysicalDeviceRasterizationOrderAttachmentAccessFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_RASTERIZATION_ORDER_ATTACHMENT_ACCESS_FEATURES_EXT; + VkPhysicalDeviceRasterizationOrderAttachmentAccessFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_RASTERIZATION_ORDER_ATTACHMENT_ACCESS_FEATURES_EXT; + VkPhysicalDeviceShaderAtomicFloatFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SHADER_ATOMIC_FLOAT_FEATURES_EXT; + VkPhysicalDeviceShaderAtomicFloatFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SHADER_ATOMIC_FLOAT_FEATURES_EXT; + VkPhysicalDeviceShaderAtomicFloatFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SHADER_ATOMIC_FLOAT_FEATURES_EXT; + VkPhysicalDeviceShaderAtomicFloatFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SHADER_ATOMIC_FLOAT_FEATURES_EXT; + VkPhysicalDeviceShaderAtomicFloatFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SHADER_ATOMIC_FLOAT_FEATURES_EXT; + VkPhysicalDeviceShaderAtomicFloatFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SHADER_ATOMIC_FLOAT_FEATURES_EXT; + VkPhysicalDeviceShaderAtomicFloatFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SHADER_ATOMIC_FLOAT_FEATURES_EXT; + VkPhysicalDeviceShaderAtomicFloatFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SHADER_ATOMIC_FLOAT_FEATURES_EXT; + VkPhysicalDeviceShaderAtomicFloatFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SHADER_ATOMIC_FLOAT_FEATURES_EXT; + VkPhysicalDeviceShaderAtomicFloatFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SHADER_ATOMIC_FLOAT_FEATURES_EXT; + VkPhysicalDeviceShaderAtomicFloatFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SHADER_ATOMIC_FLOAT_FEATURES_EXT; + VkPhysicalDeviceShaderAtomicFloatFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SHADER_ATOMIC_FLOAT_FEATURES_EXT; + VkPhysicalDeviceShaderAtomicFloat2FeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SHADER_ATOMIC_FLOAT_2_FEATURES_EXT; + VkPhysicalDeviceShaderAtomicFloat2FeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SHADER_ATOMIC_FLOAT_2_FEATURES_EXT; + VkPhysicalDeviceShaderAtomicFloat2FeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SHADER_ATOMIC_FLOAT_2_FEATURES_EXT; + VkPhysicalDeviceShaderAtomicFloat2FeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SHADER_ATOMIC_FLOAT_2_FEATURES_EXT; + VkPhysicalDeviceShaderAtomicFloat2FeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SHADER_ATOMIC_FLOAT_2_FEATURES_EXT; + VkPhysicalDeviceShaderAtomicFloat2FeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SHADER_ATOMIC_FLOAT_2_FEATURES_EXT; + VkPhysicalDeviceShaderAtomicFloat2FeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SHADER_ATOMIC_FLOAT_2_FEATURES_EXT; + VkPhysicalDeviceShaderAtomicFloat2FeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SHADER_ATOMIC_FLOAT_2_FEATURES_EXT; + VkPhysicalDeviceShaderAtomicFloat2FeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SHADER_ATOMIC_FLOAT_2_FEATURES_EXT; + VkPhysicalDeviceShaderAtomicFloat2FeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SHADER_ATOMIC_FLOAT_2_FEATURES_EXT; + VkPhysicalDeviceShaderAtomicFloat2FeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SHADER_ATOMIC_FLOAT_2_FEATURES_EXT; + VkPhysicalDeviceShaderAtomicFloat2FeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SHADER_ATOMIC_FLOAT_2_FEATURES_EXT; + VkPhysicalDeviceShaderFloat8FeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SHADER_FLOAT8_FEATURES_EXT; + VkPhysicalDeviceShaderFloat8FeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SHADER_FLOAT8_FEATURES_EXT; + VkPhysicalDeviceShaderImageAtomicInt64FeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SHADER_IMAGE_ATOMIC_INT64_FEATURES_EXT; + VkPhysicalDeviceShaderImageAtomicInt64FeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SHADER_IMAGE_ATOMIC_INT64_FEATURES_EXT; + VkPhysicalDeviceShaderModuleIdentifierFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SHADER_MODULE_IDENTIFIER_FEATURES_EXT; + VkPhysicalDeviceShaderObjectFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SHADER_OBJECT_FEATURES_EXT; + VkPhysicalDeviceShaderReplicatedCompositesFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SHADER_REPLICATED_COMPOSITES_FEATURES_EXT; + VkPhysicalDeviceShaderTileImageFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SHADER_TILE_IMAGE_FEATURES_EXT; + VkPhysicalDeviceShaderTileImageFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SHADER_TILE_IMAGE_FEATURES_EXT; + VkPhysicalDeviceShaderTileImageFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SHADER_TILE_IMAGE_FEATURES_EXT; + VkPhysicalDeviceSubpassMergeFeedbackFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SUBPASS_MERGE_FEEDBACK_FEATURES_EXT; + VkPhysicalDeviceTexelBufferAlignmentFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_TEXEL_BUFFER_ALIGNMENT_FEATURES_EXT; + VkPhysicalDeviceTransformFeedbackFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_TRANSFORM_FEEDBACK_FEATURES_EXT; + VkPhysicalDeviceTransformFeedbackFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_TRANSFORM_FEEDBACK_FEATURES_EXT; + VkPhysicalDeviceVertexAttributeRobustnessFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_VERTEX_ATTRIBUTE_ROBUSTNESS_FEATURES_EXT; + VkPhysicalDeviceVertexInputDynamicStateFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_VERTEX_INPUT_DYNAMIC_STATE_FEATURES_EXT; + VkPhysicalDeviceYcbcr2Plane444FormatsFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_YCBCR_2_PLANE_444_FORMATS_FEATURES_EXT; + VkPhysicalDeviceYcbcrImageArraysFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_YCBCR_IMAGE_ARRAYS_FEATURES_EXT; + VkPhysicalDeviceZeroInitializeDeviceMemoryFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_ZERO_INITIALIZE_DEVICE_MEMORY_FEATURES_EXT; + } + + + void _link() { + + // Link the Feature structures + decodeModeSharedExponent = &(VkPhysicalDeviceASTCDecodeFeaturesEXT::decodeModeSharedExponent); + reportAddressBinding = &(VkPhysicalDeviceAddressBindingReportFeaturesEXT::reportAddressBinding); + attachmentFeedbackLoopDynamicState = &(VkPhysicalDeviceAttachmentFeedbackLoopDynamicStateFeaturesEXT::attachmentFeedbackLoopDynamicState); + attachmentFeedbackLoopLayout = &(VkPhysicalDeviceAttachmentFeedbackLoopLayoutFeaturesEXT::attachmentFeedbackLoopLayout); + advancedBlendCoherentOperations = &(VkPhysicalDeviceBlendOperationAdvancedFeaturesEXT::advancedBlendCoherentOperations); + borderColorSwizzle = &(VkPhysicalDeviceBorderColorSwizzleFeaturesEXT::borderColorSwizzle); + borderColorSwizzleFromImage = &(VkPhysicalDeviceBorderColorSwizzleFeaturesEXT::borderColorSwizzleFromImage); + bufferDeviceAddress = &(VkPhysicalDeviceBufferDeviceAddressFeaturesEXT::bufferDeviceAddress); + bufferDeviceAddressCaptureReplay = &(VkPhysicalDeviceBufferDeviceAddressFeaturesEXT::bufferDeviceAddressCaptureReplay); + bufferDeviceAddressMultiDevice = &(VkPhysicalDeviceBufferDeviceAddressFeaturesEXT::bufferDeviceAddressMultiDevice); + formatA4R4G4B4 = &(VkPhysicalDevice4444FormatsFeaturesEXT::formatA4R4G4B4); + formatA4B4G4R4 = &(VkPhysicalDevice4444FormatsFeaturesEXT::formatA4B4G4R4); + colorWriteEnable = &(VkPhysicalDeviceColorWriteEnableFeaturesEXT::colorWriteEnable); + conditionalRendering = &(VkPhysicalDeviceConditionalRenderingFeaturesEXT::conditionalRendering); + inheritedConditionalRendering = &(VkPhysicalDeviceConditionalRenderingFeaturesEXT::inheritedConditionalRendering); + customBorderColors = &(VkPhysicalDeviceCustomBorderColorFeaturesEXT::customBorderColors); + customBorderColorWithoutFormat = &(VkPhysicalDeviceCustomBorderColorFeaturesEXT::customBorderColorWithoutFormat); + depthBiasControl = &(VkPhysicalDeviceDepthBiasControlFeaturesEXT::depthBiasControl); + leastRepresentableValueForceUnormRepresentation = &(VkPhysicalDeviceDepthBiasControlFeaturesEXT::leastRepresentableValueForceUnormRepresentation); + floatRepresentation = &(VkPhysicalDeviceDepthBiasControlFeaturesEXT::floatRepresentation); + depthBiasExact = &(VkPhysicalDeviceDepthBiasControlFeaturesEXT::depthBiasExact); + depthClampControl = &(VkPhysicalDeviceDepthClampControlFeaturesEXT::depthClampControl); + depthClipControl = &(VkPhysicalDeviceDepthClipControlFeaturesEXT::depthClipControl); + depthClipEnable = &(VkPhysicalDeviceDepthClipEnableFeaturesEXT::depthClipEnable); + descriptorBuffer = &(VkPhysicalDeviceDescriptorBufferFeaturesEXT::descriptorBuffer); + descriptorBufferCaptureReplay = &(VkPhysicalDeviceDescriptorBufferFeaturesEXT::descriptorBufferCaptureReplay); + descriptorBufferImageLayoutIgnored = &(VkPhysicalDeviceDescriptorBufferFeaturesEXT::descriptorBufferImageLayoutIgnored); + descriptorBufferPushDescriptors = &(VkPhysicalDeviceDescriptorBufferFeaturesEXT::descriptorBufferPushDescriptors); + deviceGeneratedCommands = &(VkPhysicalDeviceDeviceGeneratedCommandsFeaturesEXT::deviceGeneratedCommands); + dynamicGeneratedPipelineLayout = &(VkPhysicalDeviceDeviceGeneratedCommandsFeaturesEXT::dynamicGeneratedPipelineLayout); + deviceMemoryReport = &(VkPhysicalDeviceDeviceMemoryReportFeaturesEXT::deviceMemoryReport); + dynamicRenderingUnusedAttachments = &(VkPhysicalDeviceDynamicRenderingUnusedAttachmentsFeaturesEXT::dynamicRenderingUnusedAttachments); + extendedDynamicState = &(VkPhysicalDeviceExtendedDynamicStateFeaturesEXT::extendedDynamicState); + extendedDynamicState2 = &(VkPhysicalDeviceExtendedDynamicState2FeaturesEXT::extendedDynamicState2); + extendedDynamicState2LogicOp = &(VkPhysicalDeviceExtendedDynamicState2FeaturesEXT::extendedDynamicState2LogicOp); + extendedDynamicState2PatchControlPoints = &(VkPhysicalDeviceExtendedDynamicState2FeaturesEXT::extendedDynamicState2PatchControlPoints); + extendedDynamicState3TessellationDomainOrigin = &(VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::extendedDynamicState3TessellationDomainOrigin); + extendedDynamicState3DepthClampEnable = &(VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::extendedDynamicState3DepthClampEnable); + extendedDynamicState3PolygonMode = &(VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::extendedDynamicState3PolygonMode); + extendedDynamicState3RasterizationSamples = &(VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::extendedDynamicState3RasterizationSamples); + extendedDynamicState3SampleMask = &(VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::extendedDynamicState3SampleMask); + extendedDynamicState3AlphaToCoverageEnable = &(VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::extendedDynamicState3AlphaToCoverageEnable); + extendedDynamicState3AlphaToOneEnable = &(VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::extendedDynamicState3AlphaToOneEnable); + extendedDynamicState3LogicOpEnable = &(VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::extendedDynamicState3LogicOpEnable); + extendedDynamicState3ColorBlendEnable = &(VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::extendedDynamicState3ColorBlendEnable); + extendedDynamicState3ColorBlendEquation = &(VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::extendedDynamicState3ColorBlendEquation); + extendedDynamicState3ColorWriteMask = &(VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::extendedDynamicState3ColorWriteMask); + extendedDynamicState3RasterizationStream = &(VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::extendedDynamicState3RasterizationStream); + extendedDynamicState3ConservativeRasterizationMode = &(VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::extendedDynamicState3ConservativeRasterizationMode); + extendedDynamicState3ExtraPrimitiveOverestimationSize = &(VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::extendedDynamicState3ExtraPrimitiveOverestimationSize); + extendedDynamicState3DepthClipEnable = &(VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::extendedDynamicState3DepthClipEnable); + extendedDynamicState3SampleLocationsEnable = &(VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::extendedDynamicState3SampleLocationsEnable); + extendedDynamicState3ColorBlendAdvanced = &(VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::extendedDynamicState3ColorBlendAdvanced); + extendedDynamicState3ProvokingVertexMode = &(VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::extendedDynamicState3ProvokingVertexMode); + extendedDynamicState3LineRasterizationMode = &(VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::extendedDynamicState3LineRasterizationMode); + extendedDynamicState3LineStippleEnable = &(VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::extendedDynamicState3LineStippleEnable); + extendedDynamicState3DepthClipNegativeOneToOne = &(VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::extendedDynamicState3DepthClipNegativeOneToOne); + extendedDynamicState3ViewportWScalingEnable = &(VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::extendedDynamicState3ViewportWScalingEnable); + extendedDynamicState3ViewportSwizzle = &(VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::extendedDynamicState3ViewportSwizzle); + extendedDynamicState3CoverageToColorEnable = &(VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::extendedDynamicState3CoverageToColorEnable); + extendedDynamicState3CoverageToColorLocation = &(VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::extendedDynamicState3CoverageToColorLocation); + extendedDynamicState3CoverageModulationMode = &(VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::extendedDynamicState3CoverageModulationMode); + extendedDynamicState3CoverageModulationTableEnable = &(VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::extendedDynamicState3CoverageModulationTableEnable); + extendedDynamicState3CoverageModulationTable = &(VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::extendedDynamicState3CoverageModulationTable); + extendedDynamicState3CoverageReductionMode = &(VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::extendedDynamicState3CoverageReductionMode); + extendedDynamicState3RepresentativeFragmentTestEnable = &(VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::extendedDynamicState3RepresentativeFragmentTestEnable); + extendedDynamicState3ShadingRateImageEnable = &(VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::extendedDynamicState3ShadingRateImageEnable); + deviceFault = &(VkPhysicalDeviceFaultFeaturesEXT::deviceFault); + deviceFaultVendorBinary = &(VkPhysicalDeviceFaultFeaturesEXT::deviceFaultVendorBinary); + fragmentDensityMap = &(VkPhysicalDeviceFragmentDensityMapFeaturesEXT::fragmentDensityMap); + fragmentDensityMapDynamic = &(VkPhysicalDeviceFragmentDensityMapFeaturesEXT::fragmentDensityMapDynamic); + fragmentDensityMapNonSubsampledImages = &(VkPhysicalDeviceFragmentDensityMapFeaturesEXT::fragmentDensityMapNonSubsampledImages); + fragmentDensityMapDeferred = &(VkPhysicalDeviceFragmentDensityMap2FeaturesEXT::fragmentDensityMapDeferred); + fragmentDensityMapOffset = &(VkPhysicalDeviceFragmentDensityMapOffsetFeaturesEXT::fragmentDensityMapOffset); + fragmentShaderSampleInterlock = &(VkPhysicalDeviceFragmentShaderInterlockFeaturesEXT::fragmentShaderSampleInterlock); + fragmentShaderPixelInterlock = &(VkPhysicalDeviceFragmentShaderInterlockFeaturesEXT::fragmentShaderPixelInterlock); + fragmentShaderShadingRateInterlock = &(VkPhysicalDeviceFragmentShaderInterlockFeaturesEXT::fragmentShaderShadingRateInterlock); + frameBoundary = &(VkPhysicalDeviceFrameBoundaryFeaturesEXT::frameBoundary); + graphicsPipelineLibrary = &(VkPhysicalDeviceGraphicsPipelineLibraryFeaturesEXT::graphicsPipelineLibrary); + image2DViewOf3D = &(VkPhysicalDeviceImage2DViewOf3DFeaturesEXT::image2DViewOf3D); + sampler2DViewOf3D = &(VkPhysicalDeviceImage2DViewOf3DFeaturesEXT::sampler2DViewOf3D); + imageCompressionControl = &(VkPhysicalDeviceImageCompressionControlFeaturesEXT::imageCompressionControl); + imageCompressionControlSwapchain = &(VkPhysicalDeviceImageCompressionControlSwapchainFeaturesEXT::imageCompressionControlSwapchain); + imageSlicedViewOf3D = &(VkPhysicalDeviceImageSlicedViewOf3DFeaturesEXT::imageSlicedViewOf3D); + imageMinLod = &(VkPhysicalDeviceImageViewMinLodFeaturesEXT::minLod); + legacyDithering = &(VkPhysicalDeviceLegacyDitheringFeaturesEXT::legacyDithering); + legacyVertexAttributes = &(VkPhysicalDeviceLegacyVertexAttributesFeaturesEXT::legacyVertexAttributes); + memoryMapPlaced = &(VkPhysicalDeviceMapMemoryPlacedFeaturesEXT::memoryMapPlaced); + memoryMapRangePlaced = &(VkPhysicalDeviceMapMemoryPlacedFeaturesEXT::memoryMapRangePlaced); + memoryUnmapReserve = &(VkPhysicalDeviceMapMemoryPlacedFeaturesEXT::memoryUnmapReserve); + memoryPriority = &(VkPhysicalDeviceMemoryPriorityFeaturesEXT::memoryPriority); + taskShader = &(VkPhysicalDeviceMeshShaderFeaturesEXT::taskShader); + meshShader = &(VkPhysicalDeviceMeshShaderFeaturesEXT::meshShader); + multiviewMeshShader = &(VkPhysicalDeviceMeshShaderFeaturesEXT::multiviewMeshShader); + primitiveFragmentShadingRateMeshShader = &(VkPhysicalDeviceMeshShaderFeaturesEXT::primitiveFragmentShadingRateMeshShader); + meshShaderQueries = &(VkPhysicalDeviceMeshShaderFeaturesEXT::meshShaderQueries); + multiDraw = &(VkPhysicalDeviceMultiDrawFeaturesEXT::multiDraw); + multisampledRenderToSingleSampled = &(VkPhysicalDeviceMultisampledRenderToSingleSampledFeaturesEXT::multisampledRenderToSingleSampled); + mutableDescriptorType = &(VkPhysicalDeviceMutableDescriptorTypeFeaturesEXT::mutableDescriptorType); + nestedCommandBuffer = &(VkPhysicalDeviceNestedCommandBufferFeaturesEXT::nestedCommandBuffer); + nestedCommandBufferRendering = &(VkPhysicalDeviceNestedCommandBufferFeaturesEXT::nestedCommandBufferRendering); + nestedCommandBufferSimultaneousUse = &(VkPhysicalDeviceNestedCommandBufferFeaturesEXT::nestedCommandBufferSimultaneousUse); + nonSeamlessCubeMap = &(VkPhysicalDeviceNonSeamlessCubeMapFeaturesEXT::nonSeamlessCubeMap); + micromap = &(VkPhysicalDeviceOpacityMicromapFeaturesEXT::micromap); + micromapCaptureReplay = &(VkPhysicalDeviceOpacityMicromapFeaturesEXT::micromapCaptureReplay); + micromapHostCommands = &(VkPhysicalDeviceOpacityMicromapFeaturesEXT::micromapHostCommands); + pageableDeviceLocalMemory = &(VkPhysicalDevicePageableDeviceLocalMemoryFeaturesEXT::pageableDeviceLocalMemory); + pipelineLibraryGroupHandles = &(VkPhysicalDevicePipelineLibraryGroupHandlesFeaturesEXT::pipelineLibraryGroupHandles); + pipelinePropertiesIdentifier = &(VkPhysicalDevicePipelinePropertiesFeaturesEXT::pipelinePropertiesIdentifier); + primitiveTopologyListRestart = &(VkPhysicalDevicePrimitiveTopologyListRestartFeaturesEXT::primitiveTopologyListRestart); + primitiveTopologyPatchListRestart = &(VkPhysicalDevicePrimitiveTopologyListRestartFeaturesEXT::primitiveTopologyPatchListRestart); + primitivesGeneratedQuery = &(VkPhysicalDevicePrimitivesGeneratedQueryFeaturesEXT::primitivesGeneratedQuery); + primitivesGeneratedQueryWithRasterizerDiscard = &(VkPhysicalDevicePrimitivesGeneratedQueryFeaturesEXT::primitivesGeneratedQueryWithRasterizerDiscard); + primitivesGeneratedQueryWithNonZeroStreams = &(VkPhysicalDevicePrimitivesGeneratedQueryFeaturesEXT::primitivesGeneratedQueryWithNonZeroStreams); + provokingVertexLast = &(VkPhysicalDeviceProvokingVertexFeaturesEXT::provokingVertexLast); + transformFeedbackPreservesProvokingVertex = &(VkPhysicalDeviceProvokingVertexFeaturesEXT::transformFeedbackPreservesProvokingVertex); + formatRgba10x6WithoutYCbCrSampler = &(VkPhysicalDeviceRGBA10X6FormatsFeaturesEXT::formatRgba10x6WithoutYCbCrSampler); + rasterizationOrderColorAttachmentAccess = &(VkPhysicalDeviceRasterizationOrderAttachmentAccessFeaturesEXT::rasterizationOrderColorAttachmentAccess); + rasterizationOrderDepthAttachmentAccess = &(VkPhysicalDeviceRasterizationOrderAttachmentAccessFeaturesEXT::rasterizationOrderDepthAttachmentAccess); + rasterizationOrderStencilAttachmentAccess = &(VkPhysicalDeviceRasterizationOrderAttachmentAccessFeaturesEXT::rasterizationOrderStencilAttachmentAccess); + shaderBufferFloat32Atomics = &(VkPhysicalDeviceShaderAtomicFloatFeaturesEXT::shaderBufferFloat32Atomics); + shaderBufferFloat32AtomicAdd = &(VkPhysicalDeviceShaderAtomicFloatFeaturesEXT::shaderBufferFloat32AtomicAdd); + shaderBufferFloat64Atomics = &(VkPhysicalDeviceShaderAtomicFloatFeaturesEXT::shaderBufferFloat64Atomics); + shaderBufferFloat64AtomicAdd = &(VkPhysicalDeviceShaderAtomicFloatFeaturesEXT::shaderBufferFloat64AtomicAdd); + shaderSharedFloat32Atomics = &(VkPhysicalDeviceShaderAtomicFloatFeaturesEXT::shaderSharedFloat32Atomics); + shaderSharedFloat32AtomicAdd = &(VkPhysicalDeviceShaderAtomicFloatFeaturesEXT::shaderSharedFloat32AtomicAdd); + shaderSharedFloat64Atomics = &(VkPhysicalDeviceShaderAtomicFloatFeaturesEXT::shaderSharedFloat64Atomics); + shaderSharedFloat64AtomicAdd = &(VkPhysicalDeviceShaderAtomicFloatFeaturesEXT::shaderSharedFloat64AtomicAdd); + shaderImageFloat32Atomics = &(VkPhysicalDeviceShaderAtomicFloatFeaturesEXT::shaderImageFloat32Atomics); + shaderImageFloat32AtomicAdd = &(VkPhysicalDeviceShaderAtomicFloatFeaturesEXT::shaderImageFloat32AtomicAdd); + sparseImageFloat32Atomics = &(VkPhysicalDeviceShaderAtomicFloatFeaturesEXT::sparseImageFloat32Atomics); + sparseImageFloat32AtomicAdd = &(VkPhysicalDeviceShaderAtomicFloatFeaturesEXT::sparseImageFloat32AtomicAdd); + shaderBufferFloat16Atomics = &(VkPhysicalDeviceShaderAtomicFloat2FeaturesEXT::shaderBufferFloat16Atomics); + shaderBufferFloat16AtomicAdd = &(VkPhysicalDeviceShaderAtomicFloat2FeaturesEXT::shaderBufferFloat16AtomicAdd); + shaderBufferFloat16AtomicMinMax = &(VkPhysicalDeviceShaderAtomicFloat2FeaturesEXT::shaderBufferFloat16AtomicMinMax); + shaderBufferFloat32AtomicMinMax = &(VkPhysicalDeviceShaderAtomicFloat2FeaturesEXT::shaderBufferFloat32AtomicMinMax); + shaderBufferFloat64AtomicMinMax = &(VkPhysicalDeviceShaderAtomicFloat2FeaturesEXT::shaderBufferFloat64AtomicMinMax); + shaderSharedFloat16Atomics = &(VkPhysicalDeviceShaderAtomicFloat2FeaturesEXT::shaderSharedFloat16Atomics); + shaderSharedFloat16AtomicAdd = &(VkPhysicalDeviceShaderAtomicFloat2FeaturesEXT::shaderSharedFloat16AtomicAdd); + shaderSharedFloat16AtomicMinMax = &(VkPhysicalDeviceShaderAtomicFloat2FeaturesEXT::shaderSharedFloat16AtomicMinMax); + shaderSharedFloat32AtomicMinMax = &(VkPhysicalDeviceShaderAtomicFloat2FeaturesEXT::shaderSharedFloat32AtomicMinMax); + shaderSharedFloat64AtomicMinMax = &(VkPhysicalDeviceShaderAtomicFloat2FeaturesEXT::shaderSharedFloat64AtomicMinMax); + shaderImageFloat32AtomicMinMax = &(VkPhysicalDeviceShaderAtomicFloat2FeaturesEXT::shaderImageFloat32AtomicMinMax); + sparseImageFloat32AtomicMinMax = &(VkPhysicalDeviceShaderAtomicFloat2FeaturesEXT::sparseImageFloat32AtomicMinMax); + shaderFloat8 = &(VkPhysicalDeviceShaderFloat8FeaturesEXT::shaderFloat8); + shaderFloat8CooperativeMatrix = &(VkPhysicalDeviceShaderFloat8FeaturesEXT::shaderFloat8CooperativeMatrix); + shaderImageInt64Atomics = &(VkPhysicalDeviceShaderImageAtomicInt64FeaturesEXT::shaderImageInt64Atomics); + sparseImageInt64Atomics = &(VkPhysicalDeviceShaderImageAtomicInt64FeaturesEXT::sparseImageInt64Atomics); + shaderModuleIdentifier = &(VkPhysicalDeviceShaderModuleIdentifierFeaturesEXT::shaderModuleIdentifier); + shaderObject = &(VkPhysicalDeviceShaderObjectFeaturesEXT::shaderObject); + shaderReplicatedComposites = &(VkPhysicalDeviceShaderReplicatedCompositesFeaturesEXT::shaderReplicatedComposites); + shaderTileImageColorReadAccess = &(VkPhysicalDeviceShaderTileImageFeaturesEXT::shaderTileImageColorReadAccess); + shaderTileImageDepthReadAccess = &(VkPhysicalDeviceShaderTileImageFeaturesEXT::shaderTileImageDepthReadAccess); + shaderTileImageStencilReadAccess = &(VkPhysicalDeviceShaderTileImageFeaturesEXT::shaderTileImageStencilReadAccess); + subpassMergeFeedback = &(VkPhysicalDeviceSubpassMergeFeedbackFeaturesEXT::subpassMergeFeedback); + texelBufferAlignment = &(VkPhysicalDeviceTexelBufferAlignmentFeaturesEXT::texelBufferAlignment); + transformFeedback = &(VkPhysicalDeviceTransformFeedbackFeaturesEXT::transformFeedback); + geometryStreams = &(VkPhysicalDeviceTransformFeedbackFeaturesEXT::geometryStreams); + vertexAttributeRobustness = &(VkPhysicalDeviceVertexAttributeRobustnessFeaturesEXT::vertexAttributeRobustness); + vertexInputDynamicState = &(VkPhysicalDeviceVertexInputDynamicStateFeaturesEXT::vertexInputDynamicState); + ycbcr2plane444Formats = &(VkPhysicalDeviceYcbcr2Plane444FormatsFeaturesEXT::ycbcr2plane444Formats); + ycbcrImageArrays = &(VkPhysicalDeviceYcbcrImageArraysFeaturesEXT::ycbcrImageArrays); + zeroInitializeDeviceMemory = &(VkPhysicalDeviceZeroInitializeDeviceMemoryFeaturesEXT::zeroInitializeDeviceMemory); + + + // Daisy chain + VkPhysicalDeviceASTCDecodeFeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceAddressBindingReportFeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceAttachmentFeedbackLoopDynamicStateFeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceAttachmentFeedbackLoopLayoutFeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceBlendOperationAdvancedFeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceBorderColorSwizzleFeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceBufferDeviceAddressFeaturesEXT::pNext = static_cast(this); + VkPhysicalDevice4444FormatsFeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceColorWriteEnableFeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceConditionalRenderingFeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceCustomBorderColorFeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceDepthBiasControlFeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceDepthClampControlFeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceDepthClipControlFeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceDepthClipEnableFeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceDescriptorBufferFeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceDeviceGeneratedCommandsFeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceDeviceMemoryReportFeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceDynamicRenderingUnusedAttachmentsFeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceExtendedDynamicStateFeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceExtendedDynamicState2FeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceExtendedDynamicState3FeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceFaultFeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceFragmentDensityMapFeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceFragmentDensityMap2FeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceFragmentDensityMapOffsetFeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceFragmentShaderInterlockFeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceFrameBoundaryFeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceGraphicsPipelineLibraryFeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceImage2DViewOf3DFeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceImageCompressionControlFeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceImageCompressionControlSwapchainFeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceImageSlicedViewOf3DFeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceImageViewMinLodFeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceLegacyDitheringFeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceLegacyVertexAttributesFeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceMapMemoryPlacedFeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceMemoryPriorityFeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceMeshShaderFeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceMultiDrawFeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceMultisampledRenderToSingleSampledFeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceMutableDescriptorTypeFeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceNestedCommandBufferFeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceNonSeamlessCubeMapFeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceOpacityMicromapFeaturesEXT::pNext = static_cast(this); + VkPhysicalDevicePageableDeviceLocalMemoryFeaturesEXT::pNext = static_cast(this); + VkPhysicalDevicePipelineLibraryGroupHandlesFeaturesEXT::pNext = static_cast(this); + VkPhysicalDevicePipelinePropertiesFeaturesEXT::pNext = static_cast(this); + VkPhysicalDevicePrimitiveTopologyListRestartFeaturesEXT::pNext = static_cast(this); + VkPhysicalDevicePrimitivesGeneratedQueryFeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceProvokingVertexFeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceRGBA10X6FormatsFeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceRasterizationOrderAttachmentAccessFeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceShaderAtomicFloatFeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceShaderAtomicFloat2FeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceShaderFloat8FeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceShaderImageAtomicInt64FeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceShaderModuleIdentifierFeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceShaderObjectFeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceShaderReplicatedCompositesFeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceShaderTileImageFeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceSubpassMergeFeedbackFeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceTexelBufferAlignmentFeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceTransformFeedbackFeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceVertexAttributeRobustnessFeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceVertexInputDynamicStateFeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceYcbcr2Plane444FormatsFeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceYcbcrImageArraysFeaturesEXT::pNext = static_cast(this); + VkPhysicalDeviceZeroInitializeDeviceMemoryFeaturesEXT::pNext = nullptr; + } + +}; + + +/// +/// \brief Struct representing the available features of a physical device. +struct device_features : private VkPhysicalDeviceFeatures2, + private device_features_11, + private device_features_12, + private device_features_13, + private device_features_14, + private device_features_khr, + private device_features_ext { + +// Public Member Variables --------------------------------------------------------------------------------------------- +public: + + /// \name Core 1.0 + /// @{ + + VkPhysicalDeviceFeatures* core10 = &features; + device_features_11* core11 = this; + device_features_12* core12 = this; + device_features_13* core13 = this; + device_features_14* core14 = this; + device_features_khr* khr = this; + device_features_ext* ext = this; + + /// @} + +// Constructors & Destructor ------------------------------------------------------------------------------------------- +public: + + /// \name Constructors & Destructor + /// @{ + + /// + /// \brief Device Constructor + /// \param device The device to acquire properties from + device_features(VkPhysicalDevice device, const device_properties& properties) + : VkPhysicalDeviceFeatures2 { + .sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_FEATURES_2, + .pNext = nullptr, + .features = { }, + } + , device_features_11(properties), device_features_12(properties), device_features_13(properties) + , device_features_14(properties), device_features_khr(), device_features_ext() { + + // Attempt to use newer functions, otherwise fallback to deprecated + if (vkGetPhysicalDeviceFeatures2) { + VkPhysicalDeviceFeatures2::pNext = *core11; + core11->chain(*core12); + core12->chain(*core13); + core13->chain(*core14); + core14->chain(*khr); + khr->chain(*ext); + + vkGetPhysicalDeviceFeatures2(device, this); + } else { + vkGetPhysicalDeviceFeatures(device, &features); + } + + // TODO: Extensions + } + + /// @} + + +// Private Member Variables -------------------------------------------------------------------------------------------- +private: +}; + +} + +#endif // FENNEC_RENDERERS_VULKAN_LIB_PHYSICAL_DEVICE_FEATURES_H \ No newline at end of file diff --git a/include/fennec/renderers/vulkan/lib/physical_device_properties.h b/include/fennec/renderers/vulkan/lib/physical_device_properties.h new file mode 100644 index 0000000..9916c9a --- /dev/null +++ b/include/fennec/renderers/vulkan/lib/physical_device_properties.h @@ -0,0 +1,2661 @@ +// ===================================================================================================================== +// fennec, a free and open source game engine +// Copyright © 2025 - 2026 Medusa Slockbower +// +// This program is free software: you can redistribute it and/or modify +// it under the terms of the GNU General Public License as published by +// the Free Software Foundation, either version 3 of the License, or +// (at your option) any later version. +// +// This program is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. +// +// You should have received a copy of the GNU General Public License +// along with this program. If not, see . +// ===================================================================================================================== + +/// +/// \file fennec/renderers/vulkan/lib/physical_device_properties.h +/// \brief +/// +/// +/// \details +/// \author Medusa Slockbower +/// +/// \copyright Copyright © 2025 Medusa Slockbower ([GPLv3](https://www.gnu.org/licenses/gpl-3.0.en.html)) +/// +/// + + +#ifndef FENNEC_RENDERERS_VULKAN_LIB_PHYSICAL_DEVICE_PROPERTIES_H +#define FENNEC_RENDERERS_VULKAN_LIB_PHYSICAL_DEVICE_PROPERTIES_H + +#include + +namespace fennec::vk +{ + +// Device Properties =================================================================================================== + + +/// +/// \brief Core 1.1 Properties +struct device_properties_11 : private VkPhysicalDeviceVulkan11Properties, + + // Vulkan 1.1 Features + private VkPhysicalDeviceIDProperties, + private VkPhysicalDeviceSubgroupProperties, + private VkPhysicalDevicePointClippingProperties, + private VkPhysicalDeviceMultiviewProperties, + private VkPhysicalDeviceProtectedMemoryProperties, + private VkPhysicalDeviceMaintenance3Properties { + +// Public References --------------------------------------------------------------------------------------------------- +public: + + /// \name Properties + /// @{ + + uint8_t (*deviceUUID)[VK_UUID_SIZE]; + uint8_t (*driverUUID)[VK_UUID_SIZE]; + uint8_t (*deviceLUID)[VK_LUID_SIZE]; + uint32_t* deviceNodeMask; + VkBool32* deviceLUIDValid; + uint32_t* subgroupSize; + VkShaderStageFlags* subgroupSupportedStages; + VkSubgroupFeatureFlags* subgroupSupportedOperations; + VkBool32* subgroupQuadOperationsInAllStages; + VkPointClippingBehavior* pointClippingBehavior; + uint32_t* maxMultiviewViewCount; + uint32_t* maxMultiviewInstanceIndex; + VkBool32* protectedNoFault; + uint32_t* maxPerSetDescriptors; + VkDeviceSize* maxMemoryAllocationSize; + VkBool32 useCore; + + /// @} + + +// Methods ------------------------------------------------------------------------------------------------------------- +public: + + /// + /// \brief Default Constructor + /// \details Version information is necessary for this structure to fill itself in properly, so the default + /// constructor is not allowed. + device_properties_11() = delete; + + /// + /// \brief Features Constructor + /// \param core Properties structure to poll necessary information + device_properties_11(const VkPhysicalDeviceProperties& core) + : VkPhysicalDeviceVulkan11Properties { } + , VkPhysicalDeviceIDProperties { } + , VkPhysicalDeviceSubgroupProperties { } + , VkPhysicalDevicePointClippingProperties { } + , VkPhysicalDeviceMultiviewProperties { } + , VkPhysicalDeviceProtectedMemoryProperties { } + , VkPhysicalDeviceMaintenance3Properties { } + , deviceUUID { nullptr } + , driverUUID { nullptr } + , deviceLUID { nullptr } + , deviceNodeMask { nullptr } + , deviceLUIDValid { nullptr } + , subgroupSize { nullptr } + , subgroupSupportedStages { nullptr } + , subgroupSupportedOperations { nullptr } + , subgroupQuadOperationsInAllStages { nullptr } + , pointClippingBehavior { nullptr } + , maxMultiviewViewCount { nullptr } + , maxMultiviewInstanceIndex { nullptr } + , protectedNoFault { nullptr } + , maxPerSetDescriptors { nullptr } + , maxMemoryAllocationSize { nullptr } + , useCore { core.apiVersion >= VK_API_VERSION_1_1 } { + + _clear(); + _link(); + } + + /// + /// \brief Copy Constructor + /// \param properties The properties structure to copy + device_properties_11(const device_properties_11& properties) + : VkPhysicalDeviceVulkan11Properties { properties } + , VkPhysicalDeviceIDProperties { properties } + , VkPhysicalDeviceSubgroupProperties { properties } + , VkPhysicalDevicePointClippingProperties { properties } + , VkPhysicalDeviceMultiviewProperties { properties } + , VkPhysicalDeviceProtectedMemoryProperties { properties } + , VkPhysicalDeviceMaintenance3Properties { properties } + , deviceUUID { nullptr } + , driverUUID { nullptr } + , deviceLUID { nullptr } + , deviceNodeMask { nullptr } + , deviceLUIDValid { nullptr } + , subgroupSize { nullptr } + , subgroupSupportedStages { nullptr } + , subgroupSupportedOperations { nullptr } + , subgroupQuadOperationsInAllStages { nullptr } + , pointClippingBehavior { nullptr } + , maxMultiviewViewCount { nullptr } + , maxMultiviewInstanceIndex { nullptr } + , protectedNoFault { nullptr } + , maxPerSetDescriptors { nullptr } + , maxMemoryAllocationSize { nullptr } + , useCore { properties.useCore } { + + _link(); + } + + /// + /// \brief Copy Assignment + /// \param properties The properties to copy + /// \returns A reference to \emph{this} + device_properties_11 operator=(const device_properties_11& properties) { + if (this == &properties) { + return *this; + } + + // Copy data + VkPhysicalDeviceVulkan11Properties::operator=(properties); + VkPhysicalDeviceIDProperties::operator=(properties); + VkPhysicalDeviceSubgroupProperties::operator=(properties); + VkPhysicalDevicePointClippingProperties::operator=(properties); + VkPhysicalDeviceMultiviewProperties::operator=(properties); + VkPhysicalDeviceProtectedMemoryProperties::operator=(properties); + VkPhysicalDeviceMaintenance3Properties::operator=(properties); + useCore = properties.useCore; + + _link(); + + return *this; + } + + /// + /// \brief Chain an extension structure + /// \param next + void chain(void* next) { + + if (useCore) { + VkPhysicalDeviceVulkan11Properties::pNext = next; + } else { + VkPhysicalDeviceMaintenance3Properties::pNext = next; + } + } + + /// + /// \brief Implicit casting for chaining + operator void*() { + + if (useCore) { + return static_cast(this); + } else { + return static_cast(this); + } + } + + +// Helpers ------------------------------------------------------------------------------------------------------------- +private: + + void _clear() { + + // Clear out the struct + fennec::memset(this, 0, sizeof(*this)); + + // Set structure types + VkPhysicalDeviceVulkan11Properties::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_VULKAN_1_1_PROPERTIES; + VkPhysicalDeviceIDProperties::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_ID_PROPERTIES; + VkPhysicalDeviceSubgroupProperties::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SUBGROUP_PROPERTIES; + VkPhysicalDevicePointClippingProperties::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_POINT_CLIPPING_PROPERTIES; + VkPhysicalDeviceMultiviewProperties::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_MULTIVIEW_PROPERTIES; + VkPhysicalDeviceProtectedMemoryProperties::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_PROTECTED_MEMORY_PROPERTIES; + VkPhysicalDeviceMaintenance3Properties::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_MAINTENANCE_3_PROPERTIES; + } + + void _link() { + + // Check if we are Core 1.1 or later + if (useCore) { + + // Link to Core structure + deviceUUID = &(VkPhysicalDeviceVulkan11Properties::deviceUUID); + driverUUID = &(VkPhysicalDeviceVulkan11Properties::driverUUID); + deviceLUID = &(VkPhysicalDeviceVulkan11Properties::deviceLUID); + deviceNodeMask = &(VkPhysicalDeviceVulkan11Properties::deviceNodeMask); + deviceLUIDValid = &(VkPhysicalDeviceVulkan11Properties::deviceLUIDValid); + subgroupSize = &(VkPhysicalDeviceVulkan11Properties::subgroupSize); + subgroupSupportedStages = &(VkPhysicalDeviceVulkan11Properties::subgroupSupportedStages); + subgroupSupportedOperations = &(VkPhysicalDeviceVulkan11Properties::subgroupSupportedOperations); + subgroupQuadOperationsInAllStages = &(VkPhysicalDeviceVulkan11Properties::subgroupQuadOperationsInAllStages); + pointClippingBehavior = &(VkPhysicalDeviceVulkan11Properties::pointClippingBehavior); + maxMultiviewViewCount = &(VkPhysicalDeviceVulkan11Properties::maxMultiviewViewCount); + maxMultiviewInstanceIndex = &(VkPhysicalDeviceVulkan11Properties::maxMultiviewInstanceIndex); + protectedNoFault = &(VkPhysicalDeviceVulkan11Properties::protectedNoFault); + maxPerSetDescriptors = &(VkPhysicalDeviceVulkan11Properties::maxPerSetDescriptors); + maxMemoryAllocationSize = &(VkPhysicalDeviceVulkan11Properties::maxMemoryAllocationSize); + + VkPhysicalDeviceVulkan11Properties::pNext = nullptr; + + return; + } + + // Link to Extension structures + deviceUUID = &(VkPhysicalDeviceIDProperties::deviceUUID); + driverUUID = &(VkPhysicalDeviceIDProperties::driverUUID); + deviceLUID = &(VkPhysicalDeviceIDProperties::deviceLUID); + deviceNodeMask = &(VkPhysicalDeviceIDProperties::deviceNodeMask); + deviceLUIDValid = &(VkPhysicalDeviceIDProperties::deviceLUIDValid); + subgroupSize = &(VkPhysicalDeviceSubgroupProperties::subgroupSize); + subgroupSupportedStages = &(VkPhysicalDeviceSubgroupProperties::supportedStages); + subgroupSupportedOperations = &(VkPhysicalDeviceSubgroupProperties::supportedOperations); + subgroupQuadOperationsInAllStages = &(VkPhysicalDeviceSubgroupProperties::quadOperationsInAllStages); + pointClippingBehavior = &(VkPhysicalDevicePointClippingProperties::pointClippingBehavior); + maxMultiviewViewCount = &(VkPhysicalDeviceMultiviewProperties::maxMultiviewViewCount); + maxMultiviewInstanceIndex = &(VkPhysicalDeviceMultiviewProperties::maxMultiviewInstanceIndex); + protectedNoFault = &(VkPhysicalDeviceProtectedMemoryProperties::protectedNoFault); + maxPerSetDescriptors = &(VkPhysicalDeviceMaintenance3Properties::maxPerSetDescriptors); + maxMemoryAllocationSize = &(VkPhysicalDeviceMaintenance3Properties::maxMemoryAllocationSize); + + // Daisy Chain + VkPhysicalDeviceIDProperties::pNext = static_cast(this); + VkPhysicalDeviceSubgroupProperties::pNext = static_cast(this); + VkPhysicalDevicePointClippingProperties::pNext = static_cast(this); + VkPhysicalDeviceMultiviewProperties::pNext = static_cast(this); + VkPhysicalDeviceProtectedMemoryProperties::pNext = static_cast(this); + VkPhysicalDeviceMaintenance3Properties::pNext = nullptr; + } +}; + +/// +/// \brief Core 1.2 Properties +struct device_properties_12 : private VkPhysicalDeviceVulkan12Properties, + + private VkPhysicalDeviceDriverProperties, + private VkPhysicalDeviceFloatControlsProperties, + private VkPhysicalDeviceDescriptorIndexingProperties, + private VkPhysicalDeviceDepthStencilResolveProperties, + private VkPhysicalDeviceSamplerFilterMinmaxProperties, + private VkPhysicalDeviceTimelineSemaphoreProperties { +// Public References --------------------------------------------------------------------------------------------------- +public: + + /// \name Properties + /// @{ + + VkDriverId* driverID; + char (*driverName)[VK_MAX_DRIVER_NAME_SIZE]; + char (*driverInfo)[VK_MAX_DRIVER_INFO_SIZE]; + VkConformanceVersion* conformanceVersion; + VkShaderFloatControlsIndependence* denormBehaviorIndependence; + VkShaderFloatControlsIndependence* roundingModeIndependence; + VkBool32* shaderSignedZeroInfNanPreserveFloat16; + VkBool32* shaderSignedZeroInfNanPreserveFloat32; + VkBool32* shaderSignedZeroInfNanPreserveFloat64; + VkBool32* shaderDenormPreserveFloat16; + VkBool32* shaderDenormPreserveFloat32; + VkBool32* shaderDenormPreserveFloat64; + VkBool32* shaderDenormFlushToZeroFloat16; + VkBool32* shaderDenormFlushToZeroFloat32; + VkBool32* shaderDenormFlushToZeroFloat64; + VkBool32* shaderRoundingModeRTEFloat16; + VkBool32* shaderRoundingModeRTEFloat32; + VkBool32* shaderRoundingModeRTEFloat64; + VkBool32* shaderRoundingModeRTZFloat16; + VkBool32* shaderRoundingModeRTZFloat32; + VkBool32* shaderRoundingModeRTZFloat64; + uint32_t* maxUpdateAfterBindDescriptorsInAllPools; + VkBool32* shaderUniformBufferArrayNonUniformIndexingNative; + VkBool32* shaderSampledImageArrayNonUniformIndexingNative; + VkBool32* shaderStorageBufferArrayNonUniformIndexingNative; + VkBool32* shaderStorageImageArrayNonUniformIndexingNative; + VkBool32* shaderInputAttachmentArrayNonUniformIndexingNative; + VkBool32* robustBufferAccessUpdateAfterBind; + VkBool32* quadDivergentImplicitLod; + uint32_t* maxPerStageDescriptorUpdateAfterBindSamplers; + uint32_t* maxPerStageDescriptorUpdateAfterBindUniformBuffers; + uint32_t* maxPerStageDescriptorUpdateAfterBindStorageBuffers; + uint32_t* maxPerStageDescriptorUpdateAfterBindSampledImages; + uint32_t* maxPerStageDescriptorUpdateAfterBindStorageImages; + uint32_t* maxPerStageDescriptorUpdateAfterBindInputAttachments; + uint32_t* maxPerStageUpdateAfterBindResources; + uint32_t* maxDescriptorSetUpdateAfterBindSamplers; + uint32_t* maxDescriptorSetUpdateAfterBindUniformBuffers; + uint32_t* maxDescriptorSetUpdateAfterBindUniformBuffersDynamic; + uint32_t* maxDescriptorSetUpdateAfterBindStorageBuffers; + uint32_t* maxDescriptorSetUpdateAfterBindStorageBuffersDynamic; + uint32_t* maxDescriptorSetUpdateAfterBindSampledImages; + uint32_t* maxDescriptorSetUpdateAfterBindStorageImages; + uint32_t* maxDescriptorSetUpdateAfterBindInputAttachments; + VkResolveModeFlags* supportedDepthResolveModes; + VkResolveModeFlags* supportedStencilResolveModes; + VkBool32* independentResolveNone; + VkBool32* independentResolve; + VkBool32* filterMinmaxSingleComponentFormats; + VkBool32* filterMinmaxImageComponentMapping; + uint64_t* maxTimelineSemaphoreValueDifference; + VkSampleCountFlags* framebufferIntegerColorSampleCounts; + VkBool32 useCore; + + /// @} + + +// Method -------------------------------------------------------------------------------------------------------------- +public: + + /// + /// \brief Default Constructor + /// \details Version information is necessary for this structure to fill itself in properly, so the default + /// constructor is not allowed. + device_properties_12() = delete; + + + /// + /// \brief Features Constructor + /// \param core Properties structure to poll necessary information + device_properties_12(const VkPhysicalDeviceProperties& core) + : VkPhysicalDeviceVulkan12Properties { } + , VkPhysicalDeviceDriverProperties { } + , VkPhysicalDeviceFloatControlsProperties { } + , VkPhysicalDeviceDescriptorIndexingProperties { } + , VkPhysicalDeviceDepthStencilResolveProperties { } + , VkPhysicalDeviceSamplerFilterMinmaxProperties { } + , VkPhysicalDeviceTimelineSemaphoreProperties { } + , driverID { nullptr } + , driverName { nullptr } + , driverInfo { nullptr } + , conformanceVersion { nullptr } + , denormBehaviorIndependence { nullptr } + , roundingModeIndependence { nullptr } + , shaderSignedZeroInfNanPreserveFloat16 { nullptr } + , shaderSignedZeroInfNanPreserveFloat32 { nullptr } + , shaderSignedZeroInfNanPreserveFloat64 { nullptr } + , shaderDenormPreserveFloat16 { nullptr } + , shaderDenormPreserveFloat32 { nullptr } + , shaderDenormPreserveFloat64 { nullptr } + , shaderDenormFlushToZeroFloat16 { nullptr } + , shaderDenormFlushToZeroFloat32 { nullptr } + , shaderDenormFlushToZeroFloat64 { nullptr } + , shaderRoundingModeRTEFloat16 { nullptr } + , shaderRoundingModeRTEFloat32 { nullptr } + , shaderRoundingModeRTEFloat64 { nullptr } + , shaderRoundingModeRTZFloat16 { nullptr } + , shaderRoundingModeRTZFloat32 { nullptr } + , shaderRoundingModeRTZFloat64 { nullptr } + , maxUpdateAfterBindDescriptorsInAllPools { nullptr } + , shaderUniformBufferArrayNonUniformIndexingNative { nullptr } + , shaderSampledImageArrayNonUniformIndexingNative { nullptr } + , shaderStorageBufferArrayNonUniformIndexingNative { nullptr } + , shaderStorageImageArrayNonUniformIndexingNative { nullptr } + , shaderInputAttachmentArrayNonUniformIndexingNative { nullptr } + , robustBufferAccessUpdateAfterBind { nullptr } + , quadDivergentImplicitLod { nullptr } + , maxPerStageDescriptorUpdateAfterBindSamplers { nullptr } + , maxPerStageDescriptorUpdateAfterBindUniformBuffers { nullptr } + , maxPerStageDescriptorUpdateAfterBindStorageBuffers { nullptr } + , maxPerStageDescriptorUpdateAfterBindSampledImages { nullptr } + , maxPerStageDescriptorUpdateAfterBindStorageImages { nullptr } + , maxPerStageDescriptorUpdateAfterBindInputAttachments { nullptr } + , maxPerStageUpdateAfterBindResources { nullptr } + , maxDescriptorSetUpdateAfterBindSamplers { nullptr } + , maxDescriptorSetUpdateAfterBindUniformBuffers { nullptr } + , maxDescriptorSetUpdateAfterBindUniformBuffersDynamic { nullptr } + , maxDescriptorSetUpdateAfterBindStorageBuffers { nullptr } + , maxDescriptorSetUpdateAfterBindStorageBuffersDynamic { nullptr } + , maxDescriptorSetUpdateAfterBindSampledImages { nullptr } + , maxDescriptorSetUpdateAfterBindStorageImages { nullptr } + , maxDescriptorSetUpdateAfterBindInputAttachments { nullptr } + , supportedDepthResolveModes { nullptr } + , supportedStencilResolveModes { nullptr } + , independentResolveNone { nullptr } + , independentResolve { nullptr } + , filterMinmaxSingleComponentFormats { nullptr } + , filterMinmaxImageComponentMapping { nullptr } + , maxTimelineSemaphoreValueDifference { nullptr } + , framebufferIntegerColorSampleCounts { nullptr } + , useCore { core.apiVersion >= VK_API_VERSION_1_2 } { + + _clear(); + _link(); + } + + + /// + /// \brief Copy Constructor + /// \param properties The properties structure to copy + device_properties_12(const device_properties_12& properties) + : VkPhysicalDeviceVulkan12Properties { properties } + , VkPhysicalDeviceDriverProperties { properties } + , VkPhysicalDeviceFloatControlsProperties { properties } + , VkPhysicalDeviceDescriptorIndexingProperties { properties } + , VkPhysicalDeviceDepthStencilResolveProperties { properties } + , VkPhysicalDeviceSamplerFilterMinmaxProperties { properties } + , VkPhysicalDeviceTimelineSemaphoreProperties { properties } + , driverID { nullptr } + , driverName { nullptr } + , driverInfo { nullptr } + , conformanceVersion { nullptr } + , denormBehaviorIndependence { nullptr } + , roundingModeIndependence { nullptr } + , shaderSignedZeroInfNanPreserveFloat16 { nullptr } + , shaderSignedZeroInfNanPreserveFloat32 { nullptr } + , shaderSignedZeroInfNanPreserveFloat64 { nullptr } + , shaderDenormPreserveFloat16 { nullptr } + , shaderDenormPreserveFloat32 { nullptr } + , shaderDenormPreserveFloat64 { nullptr } + , shaderDenormFlushToZeroFloat16 { nullptr } + , shaderDenormFlushToZeroFloat32 { nullptr } + , shaderDenormFlushToZeroFloat64 { nullptr } + , shaderRoundingModeRTEFloat16 { nullptr } + , shaderRoundingModeRTEFloat32 { nullptr } + , shaderRoundingModeRTEFloat64 { nullptr } + , shaderRoundingModeRTZFloat16 { nullptr } + , shaderRoundingModeRTZFloat32 { nullptr } + , shaderRoundingModeRTZFloat64 { nullptr } + , maxUpdateAfterBindDescriptorsInAllPools { nullptr } + , shaderUniformBufferArrayNonUniformIndexingNative { nullptr } + , shaderSampledImageArrayNonUniformIndexingNative { nullptr } + , shaderStorageBufferArrayNonUniformIndexingNative { nullptr } + , shaderStorageImageArrayNonUniformIndexingNative { nullptr } + , shaderInputAttachmentArrayNonUniformIndexingNative { nullptr } + , robustBufferAccessUpdateAfterBind { nullptr } + , quadDivergentImplicitLod { nullptr } + , maxPerStageDescriptorUpdateAfterBindSamplers { nullptr } + , maxPerStageDescriptorUpdateAfterBindUniformBuffers { nullptr } + , maxPerStageDescriptorUpdateAfterBindStorageBuffers { nullptr } + , maxPerStageDescriptorUpdateAfterBindSampledImages { nullptr } + , maxPerStageDescriptorUpdateAfterBindStorageImages { nullptr } + , maxPerStageDescriptorUpdateAfterBindInputAttachments { nullptr } + , maxPerStageUpdateAfterBindResources { nullptr } + , maxDescriptorSetUpdateAfterBindSamplers { nullptr } + , maxDescriptorSetUpdateAfterBindUniformBuffers { nullptr } + , maxDescriptorSetUpdateAfterBindUniformBuffersDynamic { nullptr } + , maxDescriptorSetUpdateAfterBindStorageBuffers { nullptr } + , maxDescriptorSetUpdateAfterBindStorageBuffersDynamic { nullptr } + , maxDescriptorSetUpdateAfterBindSampledImages { nullptr } + , maxDescriptorSetUpdateAfterBindStorageImages { nullptr } + , maxDescriptorSetUpdateAfterBindInputAttachments { nullptr } + , supportedDepthResolveModes { nullptr } + , supportedStencilResolveModes { nullptr } + , independentResolveNone { nullptr } + , independentResolve { nullptr } + , filterMinmaxSingleComponentFormats { nullptr } + , filterMinmaxImageComponentMapping { nullptr } + , maxTimelineSemaphoreValueDifference { nullptr } + , framebufferIntegerColorSampleCounts { nullptr } + , useCore { properties.useCore } { + + _link(); + } + + + /// + /// \brief Copy Assignment + /// \param properties The properties to copy + /// \returns A reference to \emph{this} + device_properties_12& operator=(const device_properties_12& properties) { + if (this == &properties) { + return *this; + } + + VkPhysicalDeviceVulkan12Properties::operator=(properties); + VkPhysicalDeviceDriverProperties::operator=(properties); + VkPhysicalDeviceFloatControlsProperties::operator=(properties); + VkPhysicalDeviceDescriptorIndexingProperties::operator=(properties); + VkPhysicalDeviceDepthStencilResolveProperties::operator=(properties); + VkPhysicalDeviceSamplerFilterMinmaxProperties::operator=(properties); + VkPhysicalDeviceTimelineSemaphoreProperties::operator=(properties); + useCore = properties.useCore; + + _link(); + + return *this; + } + + /// + /// \brief Chain an extension structure + /// \param next + void chain(void* next) { + + if (useCore) { + VkPhysicalDeviceVulkan12Properties::pNext = next; + } else { + VkPhysicalDeviceTimelineSemaphoreProperties::pNext = next; + } + } + + /// + /// \brief Implicit casting for chaining + operator void*() { + + if (useCore) { + return static_cast(this); + } else { + return static_cast(this); + } + } + + +// Helpers ------------------------------------------------------------------------------------------------------------- +private: + + void _clear() { + + // Clear out the structure + fennec::memset(this, 0, sizeof(*this)); + + // Set the structure types + VkPhysicalDeviceVulkan12Properties::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_VULKAN_1_2_PROPERTIES; + VkPhysicalDeviceDriverProperties::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_DRIVER_PROPERTIES; + VkPhysicalDeviceFloatControlsProperties::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_FLOAT_CONTROLS_PROPERTIES; + VkPhysicalDeviceDescriptorIndexingProperties::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_DESCRIPTOR_INDEXING_PROPERTIES; + VkPhysicalDeviceDepthStencilResolveProperties::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_DEPTH_STENCIL_RESOLVE_PROPERTIES; + VkPhysicalDeviceSamplerFilterMinmaxProperties::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SAMPLER_FILTER_MINMAX_PROPERTIES; + VkPhysicalDeviceTimelineSemaphoreProperties::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_TIMELINE_SEMAPHORE_PROPERTIES; + } + + void _link() { + + // Check if we are Core 1.3 or later + if (useCore) { + + // Link to Core structure + driverID = &(VkPhysicalDeviceVulkan12Properties::driverID); + driverName = &(VkPhysicalDeviceVulkan12Properties::driverName); + driverInfo = &(VkPhysicalDeviceVulkan12Properties::driverInfo); + conformanceVersion = &(VkPhysicalDeviceVulkan12Properties::conformanceVersion); + denormBehaviorIndependence = &(VkPhysicalDeviceVulkan12Properties::denormBehaviorIndependence); + roundingModeIndependence = &(VkPhysicalDeviceVulkan12Properties::roundingModeIndependence); + shaderSignedZeroInfNanPreserveFloat16 = &(VkPhysicalDeviceVulkan12Properties::shaderSignedZeroInfNanPreserveFloat16); + shaderSignedZeroInfNanPreserveFloat32 = &(VkPhysicalDeviceVulkan12Properties::shaderSignedZeroInfNanPreserveFloat32); + shaderSignedZeroInfNanPreserveFloat64 = &(VkPhysicalDeviceVulkan12Properties::shaderSignedZeroInfNanPreserveFloat64); + shaderDenormPreserveFloat16 = &(VkPhysicalDeviceVulkan12Properties::shaderDenormPreserveFloat16); + shaderDenormPreserveFloat32 = &(VkPhysicalDeviceVulkan12Properties::shaderDenormPreserveFloat32); + shaderDenormPreserveFloat64 = &(VkPhysicalDeviceVulkan12Properties::shaderDenormPreserveFloat64); + shaderDenormFlushToZeroFloat16 = &(VkPhysicalDeviceVulkan12Properties::shaderDenormFlushToZeroFloat16); + shaderDenormFlushToZeroFloat32 = &(VkPhysicalDeviceVulkan12Properties::shaderDenormFlushToZeroFloat32); + shaderDenormFlushToZeroFloat64 = &(VkPhysicalDeviceVulkan12Properties::shaderDenormFlushToZeroFloat64); + shaderRoundingModeRTEFloat16 = &(VkPhysicalDeviceVulkan12Properties::shaderRoundingModeRTEFloat16); + shaderRoundingModeRTEFloat32 = &(VkPhysicalDeviceVulkan12Properties::shaderRoundingModeRTEFloat32); + shaderRoundingModeRTEFloat64 = &(VkPhysicalDeviceVulkan12Properties::shaderRoundingModeRTEFloat64); + shaderRoundingModeRTZFloat16 = &(VkPhysicalDeviceVulkan12Properties::shaderRoundingModeRTZFloat16); + shaderRoundingModeRTZFloat32 = &(VkPhysicalDeviceVulkan12Properties::shaderRoundingModeRTZFloat32); + shaderRoundingModeRTZFloat64 = &(VkPhysicalDeviceVulkan12Properties::shaderRoundingModeRTZFloat64); + maxUpdateAfterBindDescriptorsInAllPools = &(VkPhysicalDeviceVulkan12Properties::maxUpdateAfterBindDescriptorsInAllPools); + shaderUniformBufferArrayNonUniformIndexingNative = &(VkPhysicalDeviceVulkan12Properties::shaderUniformBufferArrayNonUniformIndexingNative); + shaderSampledImageArrayNonUniformIndexingNative = &(VkPhysicalDeviceVulkan12Properties::shaderSampledImageArrayNonUniformIndexingNative); + shaderStorageBufferArrayNonUniformIndexingNative = &(VkPhysicalDeviceVulkan12Properties::shaderStorageBufferArrayNonUniformIndexingNative); + shaderStorageImageArrayNonUniformIndexingNative = &(VkPhysicalDeviceVulkan12Properties::shaderStorageImageArrayNonUniformIndexingNative); + shaderInputAttachmentArrayNonUniformIndexingNative = &(VkPhysicalDeviceVulkan12Properties::shaderInputAttachmentArrayNonUniformIndexingNative); + robustBufferAccessUpdateAfterBind = &(VkPhysicalDeviceVulkan12Properties::robustBufferAccessUpdateAfterBind); + quadDivergentImplicitLod = &(VkPhysicalDeviceVulkan12Properties::quadDivergentImplicitLod); + maxPerStageDescriptorUpdateAfterBindSamplers = &(VkPhysicalDeviceVulkan12Properties::maxPerStageDescriptorUpdateAfterBindSamplers); + maxPerStageDescriptorUpdateAfterBindUniformBuffers = &(VkPhysicalDeviceVulkan12Properties::maxPerStageDescriptorUpdateAfterBindUniformBuffers); + maxPerStageDescriptorUpdateAfterBindStorageBuffers = &(VkPhysicalDeviceVulkan12Properties::maxPerStageDescriptorUpdateAfterBindStorageBuffers); + maxPerStageDescriptorUpdateAfterBindSampledImages = &(VkPhysicalDeviceVulkan12Properties::maxPerStageDescriptorUpdateAfterBindSampledImages); + maxPerStageDescriptorUpdateAfterBindStorageImages = &(VkPhysicalDeviceVulkan12Properties::maxPerStageDescriptorUpdateAfterBindStorageImages); + maxPerStageDescriptorUpdateAfterBindInputAttachments = &(VkPhysicalDeviceVulkan12Properties::maxPerStageDescriptorUpdateAfterBindInputAttachments); + maxPerStageUpdateAfterBindResources = &(VkPhysicalDeviceVulkan12Properties::maxPerStageUpdateAfterBindResources); + maxDescriptorSetUpdateAfterBindSamplers = &(VkPhysicalDeviceVulkan12Properties::maxDescriptorSetUpdateAfterBindSamplers); + maxDescriptorSetUpdateAfterBindUniformBuffers = &(VkPhysicalDeviceVulkan12Properties::maxDescriptorSetUpdateAfterBindUniformBuffers); + maxDescriptorSetUpdateAfterBindUniformBuffersDynamic = &(VkPhysicalDeviceVulkan12Properties::maxDescriptorSetUpdateAfterBindUniformBuffersDynamic); + maxDescriptorSetUpdateAfterBindStorageBuffers = &(VkPhysicalDeviceVulkan12Properties::maxDescriptorSetUpdateAfterBindStorageBuffers); + maxDescriptorSetUpdateAfterBindStorageBuffersDynamic = &(VkPhysicalDeviceVulkan12Properties::maxDescriptorSetUpdateAfterBindStorageBuffersDynamic); + maxDescriptorSetUpdateAfterBindSampledImages = &(VkPhysicalDeviceVulkan12Properties::maxDescriptorSetUpdateAfterBindSampledImages); + maxDescriptorSetUpdateAfterBindStorageImages = &(VkPhysicalDeviceVulkan12Properties::maxDescriptorSetUpdateAfterBindStorageImages); + maxDescriptorSetUpdateAfterBindInputAttachments = &(VkPhysicalDeviceVulkan12Properties::maxDescriptorSetUpdateAfterBindInputAttachments); + supportedDepthResolveModes = &(VkPhysicalDeviceVulkan12Properties::supportedDepthResolveModes); + supportedStencilResolveModes = &(VkPhysicalDeviceVulkan12Properties::supportedStencilResolveModes); + independentResolveNone = &(VkPhysicalDeviceVulkan12Properties::independentResolveNone); + independentResolve = &(VkPhysicalDeviceVulkan12Properties::independentResolve); + filterMinmaxSingleComponentFormats = &(VkPhysicalDeviceVulkan12Properties::filterMinmaxSingleComponentFormats); + filterMinmaxImageComponentMapping = &(VkPhysicalDeviceVulkan12Properties::filterMinmaxImageComponentMapping); + maxTimelineSemaphoreValueDifference = &(VkPhysicalDeviceVulkan12Properties::maxTimelineSemaphoreValueDifference); + framebufferIntegerColorSampleCounts = &(VkPhysicalDeviceVulkan12Properties::framebufferIntegerColorSampleCounts); + + VkPhysicalDeviceVulkan12Properties::pNext = nullptr; + + return; + } + + // Link to Extension structures + driverID = &(VkPhysicalDeviceDriverProperties::driverID); + driverName = &(VkPhysicalDeviceDriverProperties::driverName); + driverInfo = &(VkPhysicalDeviceDriverProperties::driverInfo); + conformanceVersion = &(VkPhysicalDeviceDriverProperties::conformanceVersion); + denormBehaviorIndependence = &(VkPhysicalDeviceFloatControlsProperties::denormBehaviorIndependence); + roundingModeIndependence = &(VkPhysicalDeviceFloatControlsProperties::roundingModeIndependence); + shaderSignedZeroInfNanPreserveFloat16 = &(VkPhysicalDeviceFloatControlsProperties::shaderSignedZeroInfNanPreserveFloat16); + shaderSignedZeroInfNanPreserveFloat32 = &(VkPhysicalDeviceFloatControlsProperties::shaderSignedZeroInfNanPreserveFloat32); + shaderSignedZeroInfNanPreserveFloat64 = &(VkPhysicalDeviceFloatControlsProperties::shaderSignedZeroInfNanPreserveFloat64); + shaderDenormPreserveFloat16 = &(VkPhysicalDeviceFloatControlsProperties::shaderDenormPreserveFloat16); + shaderDenormPreserveFloat32 = &(VkPhysicalDeviceFloatControlsProperties::shaderDenormPreserveFloat32); + shaderDenormPreserveFloat64 = &(VkPhysicalDeviceFloatControlsProperties::shaderDenormPreserveFloat64); + shaderDenormFlushToZeroFloat16 = &(VkPhysicalDeviceFloatControlsProperties::shaderDenormFlushToZeroFloat16); + shaderDenormFlushToZeroFloat32 = &(VkPhysicalDeviceFloatControlsProperties::shaderDenormFlushToZeroFloat32); + shaderDenormFlushToZeroFloat64 = &(VkPhysicalDeviceFloatControlsProperties::shaderDenormFlushToZeroFloat64); + shaderRoundingModeRTEFloat16 = &(VkPhysicalDeviceFloatControlsProperties::shaderRoundingModeRTEFloat16); + shaderRoundingModeRTEFloat32 = &(VkPhysicalDeviceFloatControlsProperties::shaderRoundingModeRTEFloat32); + shaderRoundingModeRTEFloat64 = &(VkPhysicalDeviceFloatControlsProperties::shaderRoundingModeRTEFloat64); + shaderRoundingModeRTZFloat16 = &(VkPhysicalDeviceFloatControlsProperties::shaderRoundingModeRTZFloat16); + shaderRoundingModeRTZFloat32 = &(VkPhysicalDeviceFloatControlsProperties::shaderRoundingModeRTZFloat32); + shaderRoundingModeRTZFloat64 = &(VkPhysicalDeviceFloatControlsProperties::shaderRoundingModeRTZFloat64); + maxUpdateAfterBindDescriptorsInAllPools = &(VkPhysicalDeviceDescriptorIndexingProperties::maxUpdateAfterBindDescriptorsInAllPools); + shaderUniformBufferArrayNonUniformIndexingNative = &(VkPhysicalDeviceDescriptorIndexingProperties::shaderUniformBufferArrayNonUniformIndexingNative); + shaderSampledImageArrayNonUniformIndexingNative = &(VkPhysicalDeviceDescriptorIndexingProperties::shaderSampledImageArrayNonUniformIndexingNative); + shaderStorageBufferArrayNonUniformIndexingNative = &(VkPhysicalDeviceDescriptorIndexingProperties::shaderStorageBufferArrayNonUniformIndexingNative); + shaderStorageImageArrayNonUniformIndexingNative = &(VkPhysicalDeviceDescriptorIndexingProperties::shaderStorageImageArrayNonUniformIndexingNative); + shaderInputAttachmentArrayNonUniformIndexingNative = &(VkPhysicalDeviceDescriptorIndexingProperties::shaderInputAttachmentArrayNonUniformIndexingNative); + robustBufferAccessUpdateAfterBind = &(VkPhysicalDeviceDescriptorIndexingProperties::robustBufferAccessUpdateAfterBind); + quadDivergentImplicitLod = &(VkPhysicalDeviceDescriptorIndexingProperties::quadDivergentImplicitLod); + maxPerStageDescriptorUpdateAfterBindSamplers = &(VkPhysicalDeviceDescriptorIndexingProperties::maxPerStageDescriptorUpdateAfterBindSamplers); + maxPerStageDescriptorUpdateAfterBindUniformBuffers = &(VkPhysicalDeviceDescriptorIndexingProperties::maxPerStageDescriptorUpdateAfterBindUniformBuffers); + maxPerStageDescriptorUpdateAfterBindStorageBuffers = &(VkPhysicalDeviceDescriptorIndexingProperties::maxPerStageDescriptorUpdateAfterBindStorageBuffers); + maxPerStageDescriptorUpdateAfterBindSampledImages = &(VkPhysicalDeviceDescriptorIndexingProperties::maxPerStageDescriptorUpdateAfterBindSampledImages); + maxPerStageDescriptorUpdateAfterBindStorageImages = &(VkPhysicalDeviceDescriptorIndexingProperties::maxPerStageDescriptorUpdateAfterBindStorageImages); + maxPerStageDescriptorUpdateAfterBindInputAttachments = &(VkPhysicalDeviceDescriptorIndexingProperties::maxPerStageDescriptorUpdateAfterBindInputAttachments); + maxPerStageUpdateAfterBindResources = &(VkPhysicalDeviceDescriptorIndexingProperties::maxPerStageUpdateAfterBindResources); + maxDescriptorSetUpdateAfterBindSamplers = &(VkPhysicalDeviceDescriptorIndexingProperties::maxDescriptorSetUpdateAfterBindSamplers); + maxDescriptorSetUpdateAfterBindUniformBuffers = &(VkPhysicalDeviceDescriptorIndexingProperties::maxDescriptorSetUpdateAfterBindUniformBuffers); + maxDescriptorSetUpdateAfterBindUniformBuffersDynamic = &(VkPhysicalDeviceDescriptorIndexingProperties::maxDescriptorSetUpdateAfterBindUniformBuffersDynamic); + maxDescriptorSetUpdateAfterBindStorageBuffers = &(VkPhysicalDeviceDescriptorIndexingProperties::maxDescriptorSetUpdateAfterBindStorageBuffers); + maxDescriptorSetUpdateAfterBindStorageBuffersDynamic = &(VkPhysicalDeviceDescriptorIndexingProperties::maxDescriptorSetUpdateAfterBindStorageBuffersDynamic); + maxDescriptorSetUpdateAfterBindSampledImages = &(VkPhysicalDeviceDescriptorIndexingProperties::maxDescriptorSetUpdateAfterBindSampledImages); + maxDescriptorSetUpdateAfterBindStorageImages = &(VkPhysicalDeviceDescriptorIndexingProperties::maxDescriptorSetUpdateAfterBindStorageImages); + maxDescriptorSetUpdateAfterBindInputAttachments = &(VkPhysicalDeviceDescriptorIndexingProperties::maxDescriptorSetUpdateAfterBindInputAttachments); + supportedDepthResolveModes = &(VkPhysicalDeviceDepthStencilResolveProperties::supportedDepthResolveModes); + supportedStencilResolveModes = &(VkPhysicalDeviceDepthStencilResolveProperties::supportedStencilResolveModes); + independentResolveNone = &(VkPhysicalDeviceDepthStencilResolveProperties::independentResolveNone); + independentResolve = &(VkPhysicalDeviceDepthStencilResolveProperties::independentResolve); + filterMinmaxSingleComponentFormats = &(VkPhysicalDeviceSamplerFilterMinmaxProperties::filterMinmaxSingleComponentFormats); + filterMinmaxImageComponentMapping = &(VkPhysicalDeviceSamplerFilterMinmaxProperties::filterMinmaxImageComponentMapping); + maxTimelineSemaphoreValueDifference = &(VkPhysicalDeviceTimelineSemaphoreProperties::maxTimelineSemaphoreValueDifference); + + // These features are only available in 1.2 Core +// framebufferIntegerColorSampleCounts = &(VkPhysicalDeviceTimelineSemaphoreProperties::framebufferIntegerColorSampleCounts); + + // Daisy chain + VkPhysicalDeviceDriverProperties::pNext = static_cast(this); + VkPhysicalDeviceFloatControlsProperties::pNext = static_cast(this); + VkPhysicalDeviceDescriptorIndexingProperties::pNext = static_cast(this); + VkPhysicalDeviceDepthStencilResolveProperties::pNext = static_cast(this); + VkPhysicalDeviceSamplerFilterMinmaxProperties::pNext = static_cast(this); + VkPhysicalDeviceTimelineSemaphoreProperties::pNext = nullptr; + } +}; + +/// +/// \brief Core 1.3 Properties +struct device_properties_13 : private VkPhysicalDeviceVulkan13Properties, + + private VkPhysicalDeviceSubgroupSizeControlProperties, + private VkPhysicalDeviceInlineUniformBlockProperties, + private VkPhysicalDeviceShaderIntegerDotProductProperties, + private VkPhysicalDeviceTexelBufferAlignmentProperties, + private VkPhysicalDeviceMaintenance4Properties { + +// Public References --------------------------------------------------------------------------------------------------- +public: + + /// \name Properties + /// @{ + + uint32_t* minSubgroupSize; + uint32_t* maxSubgroupSize; + uint32_t* maxComputeWorkgroupSubgroups; + VkShaderStageFlags* requiredSubgroupSizeStages; + uint32_t* maxInlineUniformBlockSize; + uint32_t* maxPerStageDescriptorInlineUniformBlocks; + uint32_t* maxPerStageDescriptorUpdateAfterBindInlineUniformBlocks; + uint32_t* maxDescriptorSetInlineUniformBlocks; + uint32_t* maxDescriptorSetUpdateAfterBindInlineUniformBlocks; + uint32_t* maxInlineUniformTotalSize; + VkBool32* integerDotProduct8BitUnsignedAccelerated; + VkBool32* integerDotProduct8BitSignedAccelerated; + VkBool32* integerDotProduct8BitMixedSignednessAccelerated; + VkBool32* integerDotProduct4x8BitPackedUnsignedAccelerated; + VkBool32* integerDotProduct4x8BitPackedSignedAccelerated; + VkBool32* integerDotProduct4x8BitPackedMixedSignednessAccelerated; + VkBool32* integerDotProduct16BitUnsignedAccelerated; + VkBool32* integerDotProduct16BitSignedAccelerated; + VkBool32* integerDotProduct16BitMixedSignednessAccelerated; + VkBool32* integerDotProduct32BitUnsignedAccelerated; + VkBool32* integerDotProduct32BitSignedAccelerated; + VkBool32* integerDotProduct32BitMixedSignednessAccelerated; + VkBool32* integerDotProduct64BitUnsignedAccelerated; + VkBool32* integerDotProduct64BitSignedAccelerated; + VkBool32* integerDotProduct64BitMixedSignednessAccelerated; + VkBool32* integerDotProductAccumulatingSaturating8BitUnsignedAccelerated; + VkBool32* integerDotProductAccumulatingSaturating8BitSignedAccelerated; + VkBool32* integerDotProductAccumulatingSaturating8BitMixedSignednessAccelerated; + VkBool32* integerDotProductAccumulatingSaturating4x8BitPackedUnsignedAccelerated; + VkBool32* integerDotProductAccumulatingSaturating4x8BitPackedSignedAccelerated; + VkBool32* integerDotProductAccumulatingSaturating4x8BitPackedMixedSignednessAccelerated; + VkBool32* integerDotProductAccumulatingSaturating16BitUnsignedAccelerated; + VkBool32* integerDotProductAccumulatingSaturating16BitSignedAccelerated; + VkBool32* integerDotProductAccumulatingSaturating16BitMixedSignednessAccelerated; + VkBool32* integerDotProductAccumulatingSaturating32BitUnsignedAccelerated; + VkBool32* integerDotProductAccumulatingSaturating32BitSignedAccelerated; + VkBool32* integerDotProductAccumulatingSaturating32BitMixedSignednessAccelerated; + VkBool32* integerDotProductAccumulatingSaturating64BitUnsignedAccelerated; + VkBool32* integerDotProductAccumulatingSaturating64BitSignedAccelerated; + VkBool32* integerDotProductAccumulatingSaturating64BitMixedSignednessAccelerated; + VkDeviceSize* storageTexelBufferOffsetAlignmentBytes; + VkBool32* storageTexelBufferOffsetSingleTexelAlignment; + VkDeviceSize* uniformTexelBufferOffsetAlignmentBytes; + VkBool32* uniformTexelBufferOffsetSingleTexelAlignment; + VkDeviceSize* maxBufferSize; + VkBool32 useCore; + + /// @} + + +// Methods ------------------------------------------------------------------------------------------------------------- +public: + + /// + /// \brief Default Constructor + /// \details Version information is necessary for this structure to fill itself in properly, so the default + /// constructor is not allowed. + device_properties_13() = delete; + + + /// + /// \brief Features Constructor + /// \param core Properties structure to poll necessary information + device_properties_13(const VkPhysicalDeviceProperties& core) + : VkPhysicalDeviceVulkan13Properties { } + , VkPhysicalDeviceSubgroupSizeControlProperties { } + , VkPhysicalDeviceInlineUniformBlockProperties { } + , VkPhysicalDeviceShaderIntegerDotProductProperties { } + , VkPhysicalDeviceTexelBufferAlignmentProperties { } + , VkPhysicalDeviceMaintenance4Properties { } + , minSubgroupSize { nullptr } + , maxSubgroupSize { nullptr } + , maxComputeWorkgroupSubgroups { nullptr } + , requiredSubgroupSizeStages { nullptr } + , maxInlineUniformBlockSize { nullptr } + , maxPerStageDescriptorInlineUniformBlocks { nullptr } + , maxPerStageDescriptorUpdateAfterBindInlineUniformBlocks { nullptr } + , maxDescriptorSetInlineUniformBlocks { nullptr } + , maxDescriptorSetUpdateAfterBindInlineUniformBlocks { nullptr } + , maxInlineUniformTotalSize { nullptr } + , integerDotProduct8BitUnsignedAccelerated { nullptr } + , integerDotProduct8BitSignedAccelerated { nullptr } + , integerDotProduct8BitMixedSignednessAccelerated { nullptr } + , integerDotProduct4x8BitPackedUnsignedAccelerated { nullptr } + , integerDotProduct4x8BitPackedSignedAccelerated { nullptr } + , integerDotProduct4x8BitPackedMixedSignednessAccelerated { nullptr } + , integerDotProduct16BitUnsignedAccelerated { nullptr } + , integerDotProduct16BitSignedAccelerated { nullptr } + , integerDotProduct16BitMixedSignednessAccelerated { nullptr } + , integerDotProduct32BitUnsignedAccelerated { nullptr } + , integerDotProduct32BitSignedAccelerated { nullptr } + , integerDotProduct32BitMixedSignednessAccelerated { nullptr } + , integerDotProduct64BitUnsignedAccelerated { nullptr } + , integerDotProduct64BitSignedAccelerated { nullptr } + , integerDotProduct64BitMixedSignednessAccelerated { nullptr } + , integerDotProductAccumulatingSaturating8BitUnsignedAccelerated { nullptr } + , integerDotProductAccumulatingSaturating8BitSignedAccelerated { nullptr } + , integerDotProductAccumulatingSaturating8BitMixedSignednessAccelerated { nullptr } + , integerDotProductAccumulatingSaturating4x8BitPackedUnsignedAccelerated { nullptr } + , integerDotProductAccumulatingSaturating4x8BitPackedSignedAccelerated { nullptr } + , integerDotProductAccumulatingSaturating4x8BitPackedMixedSignednessAccelerated { nullptr } + , integerDotProductAccumulatingSaturating16BitUnsignedAccelerated { nullptr } + , integerDotProductAccumulatingSaturating16BitSignedAccelerated { nullptr } + , integerDotProductAccumulatingSaturating16BitMixedSignednessAccelerated { nullptr } + , integerDotProductAccumulatingSaturating32BitUnsignedAccelerated { nullptr } + , integerDotProductAccumulatingSaturating32BitSignedAccelerated { nullptr } + , integerDotProductAccumulatingSaturating32BitMixedSignednessAccelerated { nullptr } + , integerDotProductAccumulatingSaturating64BitUnsignedAccelerated { nullptr } + , integerDotProductAccumulatingSaturating64BitSignedAccelerated { nullptr } + , integerDotProductAccumulatingSaturating64BitMixedSignednessAccelerated { nullptr } + , storageTexelBufferOffsetAlignmentBytes { nullptr } + , storageTexelBufferOffsetSingleTexelAlignment { nullptr } + , uniformTexelBufferOffsetAlignmentBytes { nullptr } + , uniformTexelBufferOffsetSingleTexelAlignment { nullptr } + , maxBufferSize { nullptr } + , useCore { core.apiVersion >= VK_API_VERSION_1_3 } { + + _clear(); + _link(); + } + + + /// + /// \brief Copy Constructor + /// \param properties The properties structure to copy + device_properties_13(const device_properties_13& properties) + : VkPhysicalDeviceVulkan13Properties { properties } + , VkPhysicalDeviceSubgroupSizeControlProperties { properties } + , VkPhysicalDeviceInlineUniformBlockProperties { properties } + , VkPhysicalDeviceShaderIntegerDotProductProperties { properties } + , VkPhysicalDeviceTexelBufferAlignmentProperties { properties } + , VkPhysicalDeviceMaintenance4Properties { properties } + , minSubgroupSize { nullptr } + , maxSubgroupSize { nullptr } + , maxComputeWorkgroupSubgroups { nullptr } + , requiredSubgroupSizeStages { nullptr } + , maxInlineUniformBlockSize { nullptr } + , maxPerStageDescriptorInlineUniformBlocks { nullptr } + , maxPerStageDescriptorUpdateAfterBindInlineUniformBlocks { nullptr } + , maxDescriptorSetInlineUniformBlocks { nullptr } + , maxDescriptorSetUpdateAfterBindInlineUniformBlocks { nullptr } + , maxInlineUniformTotalSize { nullptr } + , integerDotProduct8BitUnsignedAccelerated { nullptr } + , integerDotProduct8BitSignedAccelerated { nullptr } + , integerDotProduct8BitMixedSignednessAccelerated { nullptr } + , integerDotProduct4x8BitPackedUnsignedAccelerated { nullptr } + , integerDotProduct4x8BitPackedSignedAccelerated { nullptr } + , integerDotProduct4x8BitPackedMixedSignednessAccelerated { nullptr } + , integerDotProduct16BitUnsignedAccelerated { nullptr } + , integerDotProduct16BitSignedAccelerated { nullptr } + , integerDotProduct16BitMixedSignednessAccelerated { nullptr } + , integerDotProduct32BitUnsignedAccelerated { nullptr } + , integerDotProduct32BitSignedAccelerated { nullptr } + , integerDotProduct32BitMixedSignednessAccelerated { nullptr } + , integerDotProduct64BitUnsignedAccelerated { nullptr } + , integerDotProduct64BitSignedAccelerated { nullptr } + , integerDotProduct64BitMixedSignednessAccelerated { nullptr } + , integerDotProductAccumulatingSaturating8BitUnsignedAccelerated { nullptr } + , integerDotProductAccumulatingSaturating8BitSignedAccelerated { nullptr } + , integerDotProductAccumulatingSaturating8BitMixedSignednessAccelerated { nullptr } + , integerDotProductAccumulatingSaturating4x8BitPackedUnsignedAccelerated { nullptr } + , integerDotProductAccumulatingSaturating4x8BitPackedSignedAccelerated { nullptr } + , integerDotProductAccumulatingSaturating4x8BitPackedMixedSignednessAccelerated { nullptr } + , integerDotProductAccumulatingSaturating16BitUnsignedAccelerated { nullptr } + , integerDotProductAccumulatingSaturating16BitSignedAccelerated { nullptr } + , integerDotProductAccumulatingSaturating16BitMixedSignednessAccelerated { nullptr } + , integerDotProductAccumulatingSaturating32BitUnsignedAccelerated { nullptr } + , integerDotProductAccumulatingSaturating32BitSignedAccelerated { nullptr } + , integerDotProductAccumulatingSaturating32BitMixedSignednessAccelerated { nullptr } + , integerDotProductAccumulatingSaturating64BitUnsignedAccelerated { nullptr } + , integerDotProductAccumulatingSaturating64BitSignedAccelerated { nullptr } + , integerDotProductAccumulatingSaturating64BitMixedSignednessAccelerated { nullptr } + , storageTexelBufferOffsetAlignmentBytes { nullptr } + , storageTexelBufferOffsetSingleTexelAlignment { nullptr } + , uniformTexelBufferOffsetAlignmentBytes { nullptr } + , uniformTexelBufferOffsetSingleTexelAlignment { nullptr } + , maxBufferSize { nullptr } + , useCore { properties.useCore } { + + _link(); + } + + + /// + /// \brief Copy Assignment + /// \param properties The properties structure to copy + /// \returns A reference to \emph{this} + device_properties_13& operator=(const device_properties_13& properties) { + if (&properties == this) { + return *this; + } + + VkPhysicalDeviceVulkan13Properties::operator=(properties); + VkPhysicalDeviceSubgroupSizeControlProperties::operator=(properties); + VkPhysicalDeviceInlineUniformBlockProperties::operator=(properties); + VkPhysicalDeviceShaderIntegerDotProductProperties::operator=(properties); + VkPhysicalDeviceTexelBufferAlignmentProperties::operator=(properties); + VkPhysicalDeviceMaintenance4Properties::operator=(properties); + + _link(); + + return *this; + } + + /// + /// \brief Chain an extension structure + /// \param next + void chain(void* next) { + + if (useCore) { + VkPhysicalDeviceVulkan13Properties::pNext = next; + } else { + VkPhysicalDeviceMaintenance4Properties::pNext = next; + } + } + + /// + /// \brief Implicit casting for chaining + operator void*() { + + if (useCore) { + return static_cast(this); + } else { + return static_cast(this); + } + } + + +// Helpers ------------------------------------------------------------------------------------------------------------- +private: + + void _clear() { + + // Clear the structure + fennec::memset(this, 0, sizeof(*this)); + + // Set the structure types + VkPhysicalDeviceVulkan13Properties::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_VULKAN_1_3_PROPERTIES; + VkPhysicalDeviceSubgroupSizeControlProperties::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SUBGROUP_SIZE_CONTROL_PROPERTIES; + VkPhysicalDeviceInlineUniformBlockProperties::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_INLINE_UNIFORM_BLOCK_PROPERTIES; + VkPhysicalDeviceShaderIntegerDotProductProperties::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SHADER_INTEGER_DOT_PRODUCT_PROPERTIES; + VkPhysicalDeviceTexelBufferAlignmentProperties::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_TEXEL_BUFFER_ALIGNMENT_PROPERTIES; + VkPhysicalDeviceMaintenance4Properties::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_MAINTENANCE_4_PROPERTIES; + } + + void _link() { + + if (useCore) { + minSubgroupSize = &(VkPhysicalDeviceVulkan13Properties::minSubgroupSize); + maxSubgroupSize = &(VkPhysicalDeviceVulkan13Properties::maxSubgroupSize); + maxComputeWorkgroupSubgroups = &(VkPhysicalDeviceVulkan13Properties::maxComputeWorkgroupSubgroups); + requiredSubgroupSizeStages = &(VkPhysicalDeviceVulkan13Properties::requiredSubgroupSizeStages); + maxInlineUniformBlockSize = &(VkPhysicalDeviceVulkan13Properties::maxInlineUniformBlockSize); + maxPerStageDescriptorInlineUniformBlocks = &(VkPhysicalDeviceVulkan13Properties::maxPerStageDescriptorInlineUniformBlocks); + maxPerStageDescriptorUpdateAfterBindInlineUniformBlocks = &(VkPhysicalDeviceVulkan13Properties::maxPerStageDescriptorUpdateAfterBindInlineUniformBlocks); + maxDescriptorSetInlineUniformBlocks = &(VkPhysicalDeviceVulkan13Properties::maxDescriptorSetInlineUniformBlocks); + maxDescriptorSetUpdateAfterBindInlineUniformBlocks = &(VkPhysicalDeviceVulkan13Properties::maxDescriptorSetUpdateAfterBindInlineUniformBlocks); + maxInlineUniformTotalSize = &(VkPhysicalDeviceVulkan13Properties::maxInlineUniformTotalSize); + integerDotProduct8BitUnsignedAccelerated = &(VkPhysicalDeviceVulkan13Properties::integerDotProduct8BitUnsignedAccelerated); + integerDotProduct8BitSignedAccelerated = &(VkPhysicalDeviceVulkan13Properties::integerDotProduct8BitSignedAccelerated); + integerDotProduct8BitMixedSignednessAccelerated = &(VkPhysicalDeviceVulkan13Properties::integerDotProduct8BitMixedSignednessAccelerated); + integerDotProduct4x8BitPackedUnsignedAccelerated = &(VkPhysicalDeviceVulkan13Properties::integerDotProduct4x8BitPackedUnsignedAccelerated); + integerDotProduct4x8BitPackedSignedAccelerated = &(VkPhysicalDeviceVulkan13Properties::integerDotProduct4x8BitPackedSignedAccelerated); + integerDotProduct4x8BitPackedMixedSignednessAccelerated = &(VkPhysicalDeviceVulkan13Properties::integerDotProduct4x8BitPackedMixedSignednessAccelerated); + integerDotProduct16BitUnsignedAccelerated = &(VkPhysicalDeviceVulkan13Properties::integerDotProduct16BitUnsignedAccelerated); + integerDotProduct16BitSignedAccelerated = &(VkPhysicalDeviceVulkan13Properties::integerDotProduct16BitSignedAccelerated); + integerDotProduct16BitMixedSignednessAccelerated = &(VkPhysicalDeviceVulkan13Properties::integerDotProduct16BitMixedSignednessAccelerated); + integerDotProduct32BitUnsignedAccelerated = &(VkPhysicalDeviceVulkan13Properties::integerDotProduct32BitUnsignedAccelerated); + integerDotProduct32BitSignedAccelerated = &(VkPhysicalDeviceVulkan13Properties::integerDotProduct32BitSignedAccelerated); + integerDotProduct32BitMixedSignednessAccelerated = &(VkPhysicalDeviceVulkan13Properties::integerDotProduct32BitMixedSignednessAccelerated); + integerDotProduct64BitUnsignedAccelerated = &(VkPhysicalDeviceVulkan13Properties::integerDotProduct64BitUnsignedAccelerated); + integerDotProduct64BitSignedAccelerated = &(VkPhysicalDeviceVulkan13Properties::integerDotProduct64BitSignedAccelerated); + integerDotProduct64BitMixedSignednessAccelerated = &(VkPhysicalDeviceVulkan13Properties::integerDotProduct64BitMixedSignednessAccelerated); + integerDotProductAccumulatingSaturating8BitUnsignedAccelerated = &(VkPhysicalDeviceVulkan13Properties::integerDotProductAccumulatingSaturating8BitUnsignedAccelerated); + integerDotProductAccumulatingSaturating8BitSignedAccelerated = &(VkPhysicalDeviceVulkan13Properties::integerDotProductAccumulatingSaturating8BitSignedAccelerated); + integerDotProductAccumulatingSaturating8BitMixedSignednessAccelerated = &(VkPhysicalDeviceVulkan13Properties::integerDotProductAccumulatingSaturating8BitMixedSignednessAccelerated); + integerDotProductAccumulatingSaturating4x8BitPackedUnsignedAccelerated = &(VkPhysicalDeviceVulkan13Properties::integerDotProductAccumulatingSaturating4x8BitPackedUnsignedAccelerated); + integerDotProductAccumulatingSaturating4x8BitPackedSignedAccelerated = &(VkPhysicalDeviceVulkan13Properties::integerDotProductAccumulatingSaturating4x8BitPackedSignedAccelerated); + integerDotProductAccumulatingSaturating4x8BitPackedMixedSignednessAccelerated = &(VkPhysicalDeviceVulkan13Properties::integerDotProductAccumulatingSaturating4x8BitPackedMixedSignednessAccelerated); + integerDotProductAccumulatingSaturating16BitUnsignedAccelerated = &(VkPhysicalDeviceVulkan13Properties::integerDotProductAccumulatingSaturating16BitUnsignedAccelerated); + integerDotProductAccumulatingSaturating16BitSignedAccelerated = &(VkPhysicalDeviceVulkan13Properties::integerDotProductAccumulatingSaturating16BitSignedAccelerated); + integerDotProductAccumulatingSaturating16BitMixedSignednessAccelerated = &(VkPhysicalDeviceVulkan13Properties::integerDotProductAccumulatingSaturating16BitMixedSignednessAccelerated); + integerDotProductAccumulatingSaturating32BitUnsignedAccelerated = &(VkPhysicalDeviceVulkan13Properties::integerDotProductAccumulatingSaturating32BitUnsignedAccelerated); + integerDotProductAccumulatingSaturating32BitSignedAccelerated = &(VkPhysicalDeviceVulkan13Properties::integerDotProductAccumulatingSaturating32BitSignedAccelerated); + integerDotProductAccumulatingSaturating32BitMixedSignednessAccelerated = &(VkPhysicalDeviceVulkan13Properties::integerDotProductAccumulatingSaturating32BitMixedSignednessAccelerated); + integerDotProductAccumulatingSaturating64BitUnsignedAccelerated = &(VkPhysicalDeviceVulkan13Properties::integerDotProductAccumulatingSaturating64BitUnsignedAccelerated); + integerDotProductAccumulatingSaturating64BitSignedAccelerated = &(VkPhysicalDeviceVulkan13Properties::integerDotProductAccumulatingSaturating64BitSignedAccelerated); + integerDotProductAccumulatingSaturating64BitMixedSignednessAccelerated = &(VkPhysicalDeviceVulkan13Properties::integerDotProductAccumulatingSaturating64BitMixedSignednessAccelerated); + storageTexelBufferOffsetAlignmentBytes = &(VkPhysicalDeviceVulkan13Properties::storageTexelBufferOffsetAlignmentBytes); + storageTexelBufferOffsetSingleTexelAlignment = &(VkPhysicalDeviceVulkan13Properties::storageTexelBufferOffsetSingleTexelAlignment); + uniformTexelBufferOffsetAlignmentBytes = &(VkPhysicalDeviceVulkan13Properties::uniformTexelBufferOffsetAlignmentBytes); + uniformTexelBufferOffsetSingleTexelAlignment = &(VkPhysicalDeviceVulkan13Properties::uniformTexelBufferOffsetSingleTexelAlignment); + maxBufferSize = &(VkPhysicalDeviceVulkan13Properties::maxBufferSize); + + VkPhysicalDeviceVulkan13Properties::pNext = nullptr; + + return; + } + + + minSubgroupSize = &(VkPhysicalDeviceSubgroupSizeControlProperties::minSubgroupSize); + maxSubgroupSize = &(VkPhysicalDeviceSubgroupSizeControlProperties::maxSubgroupSize); + maxComputeWorkgroupSubgroups = &(VkPhysicalDeviceSubgroupSizeControlProperties::maxComputeWorkgroupSubgroups); + requiredSubgroupSizeStages = &(VkPhysicalDeviceSubgroupSizeControlProperties::requiredSubgroupSizeStages); + maxInlineUniformBlockSize = &(VkPhysicalDeviceInlineUniformBlockProperties::maxInlineUniformBlockSize); + maxPerStageDescriptorInlineUniformBlocks = &(VkPhysicalDeviceInlineUniformBlockProperties::maxPerStageDescriptorInlineUniformBlocks); + maxPerStageDescriptorUpdateAfterBindInlineUniformBlocks = &(VkPhysicalDeviceInlineUniformBlockProperties::maxPerStageDescriptorUpdateAfterBindInlineUniformBlocks); + maxDescriptorSetInlineUniformBlocks = &(VkPhysicalDeviceInlineUniformBlockProperties::maxDescriptorSetInlineUniformBlocks); + maxDescriptorSetUpdateAfterBindInlineUniformBlocks = &(VkPhysicalDeviceInlineUniformBlockProperties::maxDescriptorSetUpdateAfterBindInlineUniformBlocks); + integerDotProduct8BitUnsignedAccelerated = &(VkPhysicalDeviceShaderIntegerDotProductProperties::integerDotProduct8BitUnsignedAccelerated); + integerDotProduct8BitSignedAccelerated = &(VkPhysicalDeviceShaderIntegerDotProductProperties::integerDotProduct8BitSignedAccelerated); + integerDotProduct8BitMixedSignednessAccelerated = &(VkPhysicalDeviceShaderIntegerDotProductProperties::integerDotProduct8BitMixedSignednessAccelerated); + integerDotProduct4x8BitPackedUnsignedAccelerated = &(VkPhysicalDeviceShaderIntegerDotProductProperties::integerDotProduct4x8BitPackedUnsignedAccelerated); + integerDotProduct4x8BitPackedSignedAccelerated = &(VkPhysicalDeviceShaderIntegerDotProductProperties::integerDotProduct4x8BitPackedSignedAccelerated); + integerDotProduct4x8BitPackedMixedSignednessAccelerated = &(VkPhysicalDeviceShaderIntegerDotProductProperties::integerDotProduct4x8BitPackedMixedSignednessAccelerated); + integerDotProduct16BitUnsignedAccelerated = &(VkPhysicalDeviceShaderIntegerDotProductProperties::integerDotProduct16BitUnsignedAccelerated); + integerDotProduct16BitSignedAccelerated = &(VkPhysicalDeviceShaderIntegerDotProductProperties::integerDotProduct16BitSignedAccelerated); + integerDotProduct16BitMixedSignednessAccelerated = &(VkPhysicalDeviceShaderIntegerDotProductProperties::integerDotProduct16BitMixedSignednessAccelerated); + integerDotProduct32BitUnsignedAccelerated = &(VkPhysicalDeviceShaderIntegerDotProductProperties::integerDotProduct32BitUnsignedAccelerated); + integerDotProduct32BitSignedAccelerated = &(VkPhysicalDeviceShaderIntegerDotProductProperties::integerDotProduct32BitSignedAccelerated); + integerDotProduct32BitMixedSignednessAccelerated = &(VkPhysicalDeviceShaderIntegerDotProductProperties::integerDotProduct32BitMixedSignednessAccelerated); + integerDotProduct64BitUnsignedAccelerated = &(VkPhysicalDeviceShaderIntegerDotProductProperties::integerDotProduct64BitUnsignedAccelerated); + integerDotProduct64BitSignedAccelerated = &(VkPhysicalDeviceShaderIntegerDotProductProperties::integerDotProduct64BitSignedAccelerated); + integerDotProduct64BitMixedSignednessAccelerated = &(VkPhysicalDeviceShaderIntegerDotProductProperties::integerDotProduct64BitMixedSignednessAccelerated); + integerDotProductAccumulatingSaturating8BitUnsignedAccelerated = &(VkPhysicalDeviceShaderIntegerDotProductProperties::integerDotProductAccumulatingSaturating8BitUnsignedAccelerated); + integerDotProductAccumulatingSaturating8BitSignedAccelerated = &(VkPhysicalDeviceShaderIntegerDotProductProperties::integerDotProductAccumulatingSaturating8BitSignedAccelerated); + integerDotProductAccumulatingSaturating8BitMixedSignednessAccelerated = &(VkPhysicalDeviceShaderIntegerDotProductProperties::integerDotProductAccumulatingSaturating8BitMixedSignednessAccelerated); + integerDotProductAccumulatingSaturating4x8BitPackedUnsignedAccelerated = &(VkPhysicalDeviceShaderIntegerDotProductProperties::integerDotProductAccumulatingSaturating4x8BitPackedUnsignedAccelerated); + integerDotProductAccumulatingSaturating4x8BitPackedSignedAccelerated = &(VkPhysicalDeviceShaderIntegerDotProductProperties::integerDotProductAccumulatingSaturating4x8BitPackedSignedAccelerated); + integerDotProductAccumulatingSaturating4x8BitPackedMixedSignednessAccelerated = &(VkPhysicalDeviceShaderIntegerDotProductProperties::integerDotProductAccumulatingSaturating4x8BitPackedMixedSignednessAccelerated); + integerDotProductAccumulatingSaturating16BitUnsignedAccelerated = &(VkPhysicalDeviceShaderIntegerDotProductProperties::integerDotProductAccumulatingSaturating16BitUnsignedAccelerated); + integerDotProductAccumulatingSaturating16BitSignedAccelerated = &(VkPhysicalDeviceShaderIntegerDotProductProperties::integerDotProductAccumulatingSaturating16BitSignedAccelerated); + integerDotProductAccumulatingSaturating16BitMixedSignednessAccelerated = &(VkPhysicalDeviceShaderIntegerDotProductProperties::integerDotProductAccumulatingSaturating16BitMixedSignednessAccelerated); + integerDotProductAccumulatingSaturating32BitUnsignedAccelerated = &(VkPhysicalDeviceShaderIntegerDotProductProperties::integerDotProductAccumulatingSaturating32BitUnsignedAccelerated); + integerDotProductAccumulatingSaturating32BitSignedAccelerated = &(VkPhysicalDeviceShaderIntegerDotProductProperties::integerDotProductAccumulatingSaturating32BitSignedAccelerated); + integerDotProductAccumulatingSaturating32BitMixedSignednessAccelerated = &(VkPhysicalDeviceShaderIntegerDotProductProperties::integerDotProductAccumulatingSaturating32BitMixedSignednessAccelerated); + integerDotProductAccumulatingSaturating64BitUnsignedAccelerated = &(VkPhysicalDeviceShaderIntegerDotProductProperties::integerDotProductAccumulatingSaturating64BitUnsignedAccelerated); + integerDotProductAccumulatingSaturating64BitSignedAccelerated = &(VkPhysicalDeviceShaderIntegerDotProductProperties::integerDotProductAccumulatingSaturating64BitSignedAccelerated); + integerDotProductAccumulatingSaturating64BitMixedSignednessAccelerated = &(VkPhysicalDeviceShaderIntegerDotProductProperties::integerDotProductAccumulatingSaturating64BitMixedSignednessAccelerated); + storageTexelBufferOffsetAlignmentBytes = &(VkPhysicalDeviceTexelBufferAlignmentProperties::storageTexelBufferOffsetAlignmentBytes); + storageTexelBufferOffsetSingleTexelAlignment = &(VkPhysicalDeviceTexelBufferAlignmentProperties::storageTexelBufferOffsetSingleTexelAlignment); + uniformTexelBufferOffsetAlignmentBytes = &(VkPhysicalDeviceTexelBufferAlignmentProperties::uniformTexelBufferOffsetAlignmentBytes); + uniformTexelBufferOffsetSingleTexelAlignment = &(VkPhysicalDeviceTexelBufferAlignmentProperties::uniformTexelBufferOffsetSingleTexelAlignment); + maxBufferSize = &(VkPhysicalDeviceMaintenance4Properties::maxBufferSize); + + // These features are only available in 1.3 Core +// maxInlineUniformTotalSize = &(VkPhysicalDeviceVulkan13Properties::maxInlineUniformTotalSize); + + VkPhysicalDeviceSubgroupSizeControlProperties::pNext = static_cast(this); + VkPhysicalDeviceInlineUniformBlockProperties::pNext = static_cast(this); + VkPhysicalDeviceShaderIntegerDotProductProperties::pNext = static_cast(this); + VkPhysicalDeviceTexelBufferAlignmentProperties::pNext = static_cast(this); + VkPhysicalDeviceMaintenance4Properties::pNext = nullptr; + } +}; + +/// +/// \brief Core 1.4 Properties +struct device_properties_14 : private VkPhysicalDeviceVulkan14Properties, + private VkPhysicalDeviceLineRasterizationProperties, + private VkPhysicalDeviceVertexAttributeDivisorProperties, + private VkPhysicalDevicePushDescriptorProperties, + private VkPhysicalDeviceMaintenance5Properties, + private VkPhysicalDeviceMaintenance6Properties, + private VkPhysicalDevicePipelineRobustnessProperties, + private VkPhysicalDeviceHostImageCopyProperties { + +// Public References --------------------------------------------------------------------------------------------------- +public: + + /// \name Properties + /// @{ + + uint32_t* lineSubPixelPrecisionBits; + uint32_t* maxVertexAttribDivisor; + VkBool32* supportsNonZeroFirstInstance; + uint32_t* maxPushDescriptors; + VkBool32* dynamicRenderingLocalReadDepthStencilAttachments; + VkBool32* dynamicRenderingLocalReadMultisampledAttachments; + VkBool32* earlyFragmentMultisampleCoverageAfterSampleCounting; + VkBool32* earlyFragmentSampleMaskTestBeforeSampleCounting; + VkBool32* depthStencilSwizzleOneSupport; + VkBool32* polygonModePointSize; + VkBool32* nonStrictSinglePixelWideLinesUseParallelogram; + VkBool32* nonStrictWideLinesUseParallelogram; + VkBool32* blockTexelViewCompatibleMultipleLayers; + uint32_t* maxCombinedImageSamplerDescriptorCount; + VkBool32* fragmentShadingRateClampCombinerInputs; + VkPipelineRobustnessBufferBehavior* defaultRobustnessStorageBuffers; + VkPipelineRobustnessBufferBehavior* defaultRobustnessUniformBuffers; + VkPipelineRobustnessBufferBehavior* defaultRobustnessVertexInputs; + VkPipelineRobustnessImageBehavior* defaultRobustnessImages; + uint32_t* copySrcLayoutCount; + VkImageLayout** pCopySrcLayouts; + uint32_t* copyDstLayoutCount; + VkImageLayout** pCopyDstLayouts; + uint8_t (* optimalTilingLayoutUUID)[VK_UUID_SIZE]; + VkBool32* identicalMemoryTypeRequirements; + VkBool32 useCore; + + /// @} + + +// Methods ------------------------------------------------------------------------------------------------------------- +public: + device_properties_14() = delete; + + device_properties_14(const VkPhysicalDeviceProperties& core) + : VkPhysicalDeviceVulkan14Properties { } + , VkPhysicalDeviceLineRasterizationProperties { } + , VkPhysicalDeviceVertexAttributeDivisorProperties { } + , VkPhysicalDevicePushDescriptorProperties { } + , VkPhysicalDeviceMaintenance5Properties { } + , VkPhysicalDeviceMaintenance6Properties { } + , VkPhysicalDevicePipelineRobustnessProperties { } + , VkPhysicalDeviceHostImageCopyProperties { } + , lineSubPixelPrecisionBits { nullptr } + , maxVertexAttribDivisor { nullptr } + , supportsNonZeroFirstInstance { nullptr } + , maxPushDescriptors { nullptr } + , dynamicRenderingLocalReadDepthStencilAttachments { nullptr } + , dynamicRenderingLocalReadMultisampledAttachments { nullptr } + , earlyFragmentMultisampleCoverageAfterSampleCounting { nullptr } + , earlyFragmentSampleMaskTestBeforeSampleCounting { nullptr } + , depthStencilSwizzleOneSupport { nullptr } + , polygonModePointSize { nullptr } + , nonStrictSinglePixelWideLinesUseParallelogram { nullptr } + , nonStrictWideLinesUseParallelogram { nullptr } + , blockTexelViewCompatibleMultipleLayers { nullptr } + , maxCombinedImageSamplerDescriptorCount { nullptr } + , fragmentShadingRateClampCombinerInputs { nullptr } + , defaultRobustnessStorageBuffers { nullptr } + , defaultRobustnessUniformBuffers { nullptr } + , defaultRobustnessVertexInputs { nullptr } + , defaultRobustnessImages { nullptr } + , copySrcLayoutCount { nullptr } + , pCopySrcLayouts { nullptr } + , copyDstLayoutCount { nullptr } + , pCopyDstLayouts { nullptr } + , optimalTilingLayoutUUID { nullptr } + , identicalMemoryTypeRequirements { nullptr } + , useCore { core.apiVersion >= VK_API_VERSION_1_4 } { + + _clear(); + _link(); + } + + device_properties_14(const device_properties_14& properties) + : VkPhysicalDeviceVulkan14Properties { properties } + , VkPhysicalDeviceLineRasterizationProperties { properties } + , VkPhysicalDeviceVertexAttributeDivisorProperties { properties } + , VkPhysicalDevicePushDescriptorProperties { properties } + , VkPhysicalDeviceMaintenance5Properties { properties } + , VkPhysicalDeviceMaintenance6Properties { properties } + , VkPhysicalDevicePipelineRobustnessProperties { properties } + , VkPhysicalDeviceHostImageCopyProperties { properties } + , lineSubPixelPrecisionBits { nullptr } + , maxVertexAttribDivisor { nullptr } + , supportsNonZeroFirstInstance { nullptr } + , maxPushDescriptors { nullptr } + , dynamicRenderingLocalReadDepthStencilAttachments { nullptr } + , dynamicRenderingLocalReadMultisampledAttachments { nullptr } + , earlyFragmentMultisampleCoverageAfterSampleCounting { nullptr } + , earlyFragmentSampleMaskTestBeforeSampleCounting { nullptr } + , depthStencilSwizzleOneSupport { nullptr } + , polygonModePointSize { nullptr } + , nonStrictSinglePixelWideLinesUseParallelogram { nullptr } + , nonStrictWideLinesUseParallelogram { nullptr } + , blockTexelViewCompatibleMultipleLayers { nullptr } + , maxCombinedImageSamplerDescriptorCount { nullptr } + , fragmentShadingRateClampCombinerInputs { nullptr } + , defaultRobustnessStorageBuffers { nullptr } + , defaultRobustnessUniformBuffers { nullptr } + , defaultRobustnessVertexInputs { nullptr } + , defaultRobustnessImages { nullptr } + , copySrcLayoutCount { nullptr } + , pCopySrcLayouts { nullptr } + , copyDstLayoutCount { nullptr } + , pCopyDstLayouts { nullptr } + , optimalTilingLayoutUUID { nullptr } + , identicalMemoryTypeRequirements { nullptr } + , useCore { properties.useCore } { + + _link(); + } + + device_properties_14& operator=(const device_properties_14& properties) { + if (&properties == this) { + return *this; + } + + VkPhysicalDeviceVulkan14Properties::operator=(properties); + VkPhysicalDeviceLineRasterizationProperties::operator=(properties); + VkPhysicalDeviceVertexAttributeDivisorProperties::operator=(properties); + VkPhysicalDevicePushDescriptorProperties::operator=(properties); + VkPhysicalDeviceMaintenance5Properties::operator=(properties); + VkPhysicalDeviceMaintenance6Properties::operator=(properties); + VkPhysicalDevicePipelineRobustnessProperties::operator=(properties); + VkPhysicalDeviceHostImageCopyProperties::operator=(properties); + + _link(); + + return *this; + } + + /// + /// \brief Chain an extension structure + /// \param next + void chain(void* next) { + + if (useCore) { + VkPhysicalDeviceVulkan14Properties::pNext = next; + } else { + VkPhysicalDeviceHostImageCopyProperties::pNext = next; + } + } + + /// + /// \brief Implicit casting for chaining + operator void*() { + + if (useCore) { + return static_cast(this); + } else { + return static_cast(this); + } + } + + +// Helpers ------------------------------------------------------------------------------------------------------------- +private: + + void _clear() { + + // Clear the structure + fennec::memset(this, 0, sizeof(*this)); + + // Set the structure types + VkPhysicalDeviceVulkan14Properties::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_VULKAN_1_4_PROPERTIES; + VkPhysicalDeviceLineRasterizationProperties::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_LINE_RASTERIZATION_PROPERTIES; + VkPhysicalDeviceVertexAttributeDivisorProperties::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_VERTEX_ATTRIBUTE_DIVISOR_PROPERTIES; + VkPhysicalDevicePushDescriptorProperties::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_PUSH_DESCRIPTOR_PROPERTIES; + VkPhysicalDeviceMaintenance5Properties::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_MAINTENANCE_5_PROPERTIES; + VkPhysicalDeviceMaintenance6Properties::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_MAINTENANCE_6_PROPERTIES; + VkPhysicalDevicePipelineRobustnessProperties::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_PIPELINE_ROBUSTNESS_PROPERTIES; + VkPhysicalDeviceHostImageCopyProperties::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_HOST_IMAGE_COPY_PROPERTIES; + } + + void _link() { + + // Check if we are Core 1.4 or later + if (useCore) { + + // Link to Core Structure + lineSubPixelPrecisionBits = &(VkPhysicalDeviceVulkan14Properties::lineSubPixelPrecisionBits); + maxVertexAttribDivisor = &(VkPhysicalDeviceVulkan14Properties::maxVertexAttribDivisor); + supportsNonZeroFirstInstance = &(VkPhysicalDeviceVulkan14Properties::supportsNonZeroFirstInstance); + maxPushDescriptors = &(VkPhysicalDeviceVulkan14Properties::maxPushDescriptors); + dynamicRenderingLocalReadDepthStencilAttachments = &(VkPhysicalDeviceVulkan14Properties::dynamicRenderingLocalReadDepthStencilAttachments); + dynamicRenderingLocalReadMultisampledAttachments = &(VkPhysicalDeviceVulkan14Properties::dynamicRenderingLocalReadMultisampledAttachments); + earlyFragmentMultisampleCoverageAfterSampleCounting = &(VkPhysicalDeviceVulkan14Properties::earlyFragmentMultisampleCoverageAfterSampleCounting); + earlyFragmentSampleMaskTestBeforeSampleCounting = &(VkPhysicalDeviceVulkan14Properties::earlyFragmentSampleMaskTestBeforeSampleCounting); + depthStencilSwizzleOneSupport = &(VkPhysicalDeviceVulkan14Properties::depthStencilSwizzleOneSupport); + polygonModePointSize = &(VkPhysicalDeviceVulkan14Properties::polygonModePointSize); + nonStrictSinglePixelWideLinesUseParallelogram = &(VkPhysicalDeviceVulkan14Properties::nonStrictSinglePixelWideLinesUseParallelogram); + nonStrictWideLinesUseParallelogram = &(VkPhysicalDeviceVulkan14Properties::nonStrictWideLinesUseParallelogram); + blockTexelViewCompatibleMultipleLayers = &(VkPhysicalDeviceVulkan14Properties::blockTexelViewCompatibleMultipleLayers); + maxCombinedImageSamplerDescriptorCount = &(VkPhysicalDeviceVulkan14Properties::maxCombinedImageSamplerDescriptorCount); + fragmentShadingRateClampCombinerInputs = &(VkPhysicalDeviceVulkan14Properties::fragmentShadingRateClampCombinerInputs); + defaultRobustnessStorageBuffers = &(VkPhysicalDeviceVulkan14Properties::defaultRobustnessStorageBuffers); + defaultRobustnessUniformBuffers = &(VkPhysicalDeviceVulkan14Properties::defaultRobustnessUniformBuffers); + defaultRobustnessVertexInputs = &(VkPhysicalDeviceVulkan14Properties::defaultRobustnessVertexInputs); + defaultRobustnessImages = &(VkPhysicalDeviceVulkan14Properties::defaultRobustnessImages); + copySrcLayoutCount = &(VkPhysicalDeviceVulkan14Properties::copySrcLayoutCount); + pCopySrcLayouts = &(VkPhysicalDeviceVulkan14Properties::pCopySrcLayouts); + copyDstLayoutCount = &(VkPhysicalDeviceVulkan14Properties::copyDstLayoutCount); + pCopyDstLayouts = &(VkPhysicalDeviceVulkan14Properties::pCopyDstLayouts); + optimalTilingLayoutUUID = &(VkPhysicalDeviceVulkan14Properties::optimalTilingLayoutUUID); + identicalMemoryTypeRequirements = &(VkPhysicalDeviceVulkan14Properties::identicalMemoryTypeRequirements); + + VkPhysicalDeviceVulkan14Properties::pNext = nullptr; + + return; + } + + // Link to Extension Structures + lineSubPixelPrecisionBits = &(VkPhysicalDeviceLineRasterizationProperties::lineSubPixelPrecisionBits); + maxVertexAttribDivisor = &(VkPhysicalDeviceVertexAttributeDivisorProperties::maxVertexAttribDivisor); + supportsNonZeroFirstInstance = &(VkPhysicalDeviceVertexAttributeDivisorProperties::supportsNonZeroFirstInstance); + maxPushDescriptors = &(VkPhysicalDevicePushDescriptorProperties::maxPushDescriptors); + earlyFragmentMultisampleCoverageAfterSampleCounting = &(VkPhysicalDeviceMaintenance5Properties::earlyFragmentMultisampleCoverageAfterSampleCounting); + earlyFragmentSampleMaskTestBeforeSampleCounting = &(VkPhysicalDeviceMaintenance5Properties::earlyFragmentSampleMaskTestBeforeSampleCounting); + depthStencilSwizzleOneSupport = &(VkPhysicalDeviceMaintenance5Properties::depthStencilSwizzleOneSupport); + polygonModePointSize = &(VkPhysicalDeviceMaintenance5Properties::polygonModePointSize); + nonStrictSinglePixelWideLinesUseParallelogram = &(VkPhysicalDeviceMaintenance5Properties::nonStrictSinglePixelWideLinesUseParallelogram); + nonStrictWideLinesUseParallelogram = &(VkPhysicalDeviceMaintenance5Properties::nonStrictWideLinesUseParallelogram); + blockTexelViewCompatibleMultipleLayers = &(VkPhysicalDeviceMaintenance6Properties::blockTexelViewCompatibleMultipleLayers); + maxCombinedImageSamplerDescriptorCount = &(VkPhysicalDeviceMaintenance6Properties::maxCombinedImageSamplerDescriptorCount); + fragmentShadingRateClampCombinerInputs = &(VkPhysicalDeviceMaintenance6Properties::fragmentShadingRateClampCombinerInputs); + defaultRobustnessStorageBuffers = &(VkPhysicalDevicePipelineRobustnessProperties::defaultRobustnessStorageBuffers); + defaultRobustnessUniformBuffers = &(VkPhysicalDevicePipelineRobustnessProperties::defaultRobustnessUniformBuffers); + defaultRobustnessVertexInputs = &(VkPhysicalDevicePipelineRobustnessProperties::defaultRobustnessVertexInputs); + defaultRobustnessImages = &(VkPhysicalDevicePipelineRobustnessProperties::defaultRobustnessImages); + copySrcLayoutCount = &(VkPhysicalDeviceHostImageCopyProperties::copySrcLayoutCount); + pCopySrcLayouts = &(VkPhysicalDeviceHostImageCopyProperties::pCopySrcLayouts); + copyDstLayoutCount = &(VkPhysicalDeviceHostImageCopyProperties::copyDstLayoutCount); + pCopyDstLayouts = &(VkPhysicalDeviceHostImageCopyProperties::pCopyDstLayouts); + optimalTilingLayoutUUID = &(VkPhysicalDeviceHostImageCopyProperties::optimalTilingLayoutUUID); + identicalMemoryTypeRequirements = &(VkPhysicalDeviceHostImageCopyProperties::identicalMemoryTypeRequirements); + + // These features are only available in 1.4 Core +// dynamicRenderingLocalReadDepthStencilAttachments = &(VkPhysicalDeviceVulkan14Properties::dynamicRenderingLocalReadDepthStencilAttachments); +// dynamicRenderingLocalReadMultisampledAttachments = &(VkPhysicalDeviceVulkan14Properties::dynamicRenderingLocalReadMultisampledAttachments); + + // Daisy Chain + VkPhysicalDeviceLineRasterizationProperties::pNext = static_cast(this); + VkPhysicalDeviceVertexAttributeDivisorProperties::pNext = static_cast(this); + VkPhysicalDevicePushDescriptorProperties::pNext = static_cast(this); + VkPhysicalDeviceMaintenance5Properties::pNext = static_cast(this); + VkPhysicalDeviceMaintenance6Properties::pNext = static_cast(this); + VkPhysicalDevicePipelineRobustnessProperties::pNext = static_cast(this); + VkPhysicalDeviceHostImageCopyProperties::pNext = nullptr; + } +}; + +/// +/// \brief KHR Properties +struct device_properties_khr : private VkPhysicalDeviceAccelerationStructurePropertiesKHR, + private VkPhysicalDeviceComputeShaderDerivativesPropertiesKHR, + private VkPhysicalDeviceCooperativeMatrixPropertiesKHR, + private VkPhysicalDeviceCopyMemoryIndirectPropertiesKHR, + private VkPhysicalDeviceFragmentShaderBarycentricPropertiesKHR, + private VkPhysicalDeviceFragmentShadingRatePropertiesKHR, + private VkPhysicalDeviceLayeredApiPropertiesListKHR, + private VkPhysicalDeviceLayeredApiVulkanPropertiesKHR, + private VkPhysicalDeviceMaintenance7PropertiesKHR, + private VkPhysicalDeviceMaintenance9PropertiesKHR, + private VkPhysicalDeviceMaintenance10PropertiesKHR, + private VkPhysicalDevicePerformanceQueryPropertiesKHR, + private VkPhysicalDevicePipelineBinaryPropertiesKHR, + private VkPhysicalDevicePipelineExecutablePropertiesFeaturesKHR, + private VkPhysicalDeviceRayTracingPipelinePropertiesKHR, + private VkPhysicalDeviceRobustness2PropertiesKHR { + +// Public References --------------------------------------------------------------------------------------------------- +public: + + /// \name Properties + /// @{ + + uint64_t* maxGeometryCount; + uint64_t* maxInstanceCount; + uint64_t* maxPrimitiveCount; + uint32_t* maxPerStageDescriptorAccelerationStructures; + uint32_t* maxPerStageDescriptorUpdateAfterBindAccelerationStructures; + uint32_t* maxDescriptorSetAccelerationStructures; + uint32_t* maxDescriptorSetUpdateAfterBindAccelerationStructures; + uint32_t* minAccelerationStructureScratchOffsetAlignment; + VkBool32* meshAndTaskShaderDerivatives; + VkShaderStageFlags* cooperativeMatrixSupportedStages; + VkQueueFlags* supportedCopyQueues; + VkBool32* triStripVertexOrderIndependentOfProvokingVertex; + VkExtent2D* minFragmentShadingRateAttachmentTexelSize; + VkExtent2D* maxFragmentShadingRateAttachmentTexelSize; + uint32_t* maxFragmentShadingRateAttachmentTexelSizeAspectRatio; + VkBool32* primitiveFragmentShadingRateWithMultipleViewports; + VkBool32* layeredShadingRateAttachments; + VkBool32* fragmentShadingRateNonTrivialCombinerOps; + VkExtent2D* maxFragmentSize; + uint32_t* maxFragmentSizeAspectRatio; + uint32_t* maxFragmentShadingRateCoverageSamples; + VkSampleCountFlagBits* maxFragmentShadingRateRasterizationSamples; + VkBool32* fragmentShadingRateWithShaderDepthStencilWrites; + VkBool32* fragmentShadingRateWithSampleMask; + VkBool32* fragmentShadingRateWithShaderSampleMask; + VkBool32* fragmentShadingRateWithConservativeRasterization; + VkBool32* fragmentShadingRateWithFragmentShaderInterlock; + VkBool32* fragmentShadingRateWithCustomSampleLocations; + VkBool32* fragmentShadingRateStrictMultiplyCombiner; + uint32_t* layeredApiCount; + VkPhysicalDeviceLayeredApiPropertiesKHR** pLayeredApis; + VkPhysicalDeviceProperties2* layerProperties; + VkBool32* robustFragmentShadingRateAttachmentAccess; + VkBool32* separateDepthStencilAttachmentAccess; + uint32_t* maxDescriptorSetTotalUniformBuffersDynamic; + uint32_t* maxDescriptorSetTotalStorageBuffersDynamic; + uint32_t* maxDescriptorSetTotalBuffersDynamic; + uint32_t* maxDescriptorSetUpdateAfterBindTotalUniformBuffersDynamic; + uint32_t* maxDescriptorSetUpdateAfterBindTotalStorageBuffersDynamic; + uint32_t* maxDescriptorSetUpdateAfterBindTotalBuffersDynamic; + VkBool32* image2DViewOf3DSparse; + VkDefaultVertexAttributeValueKHR* defaultVertexAttributeValue; + VkBool32* rgba4OpaqueBlackSwizzled; + VkBool32* resolveSrgbFormatAppliesTransferFunction; + VkBool32* resolveSrgbFormatSupportsTransferFunctionControl; + VkBool32* allowCommandBufferQueryCopies; + VkBool32* pipelineBinaryInternalCache; + VkBool32* pipelineBinaryInternalCacheControl; + VkBool32* pipelineBinaryPrefersInternalCache; + VkBool32* pipelineBinaryPrecompiledInternalCache; + VkBool32* pipelineBinaryCompressedData; + VkBool32* pipelineExecutableInfo; + uint32_t* shaderGroupHandleSize; + uint32_t* maxRayRecursionDepth; + uint32_t* maxShaderGroupStride; + uint32_t* shaderGroupBaseAlignment; + uint32_t* shaderGroupHandleCaptureReplaySize; + uint32_t* maxRayDispatchInvocationCount; + uint32_t* shaderGroupHandleAlignment; + uint32_t* maxRayHitAttributeSize; + VkDeviceSize* robustStorageBufferAccessSizeAlignment; + VkDeviceSize* robustUniformBufferAccessSizeAlignment; + + /// @} + + +// Methods ------------------------------------------------------------------------------------------------------------- +public: + + device_properties_khr() + : VkPhysicalDeviceAccelerationStructurePropertiesKHR { } + , VkPhysicalDeviceComputeShaderDerivativesPropertiesKHR { } + , VkPhysicalDeviceCooperativeMatrixPropertiesKHR { } + , VkPhysicalDeviceCopyMemoryIndirectPropertiesKHR { } + , VkPhysicalDeviceFragmentShaderBarycentricPropertiesKHR { } + , VkPhysicalDeviceFragmentShadingRatePropertiesKHR { } + , VkPhysicalDeviceLayeredApiPropertiesListKHR { } + , VkPhysicalDeviceLayeredApiVulkanPropertiesKHR { } + , VkPhysicalDeviceMaintenance7PropertiesKHR { } + , VkPhysicalDeviceMaintenance9PropertiesKHR { } + , VkPhysicalDeviceMaintenance10PropertiesKHR { } + , VkPhysicalDevicePerformanceQueryPropertiesKHR { } + , VkPhysicalDevicePipelineBinaryPropertiesKHR { } + , VkPhysicalDevicePipelineExecutablePropertiesFeaturesKHR { } + , VkPhysicalDeviceRayTracingPipelinePropertiesKHR { } + , VkPhysicalDeviceRobustness2PropertiesKHR { } + , maxGeometryCount { nullptr } + , maxInstanceCount { nullptr } + , maxPrimitiveCount { nullptr } + , maxPerStageDescriptorAccelerationStructures { nullptr } + , maxPerStageDescriptorUpdateAfterBindAccelerationStructures { nullptr } + , maxDescriptorSetAccelerationStructures { nullptr } + , maxDescriptorSetUpdateAfterBindAccelerationStructures { nullptr } + , minAccelerationStructureScratchOffsetAlignment { nullptr } + , meshAndTaskShaderDerivatives { nullptr } + , cooperativeMatrixSupportedStages { nullptr } + , supportedCopyQueues { nullptr } + , triStripVertexOrderIndependentOfProvokingVertex { nullptr } + , minFragmentShadingRateAttachmentTexelSize { nullptr } + , maxFragmentShadingRateAttachmentTexelSize { nullptr } + , maxFragmentShadingRateAttachmentTexelSizeAspectRatio { nullptr } + , primitiveFragmentShadingRateWithMultipleViewports { nullptr } + , layeredShadingRateAttachments { nullptr } + , fragmentShadingRateNonTrivialCombinerOps { nullptr } + , maxFragmentSize { nullptr } + , maxFragmentSizeAspectRatio { nullptr } + , maxFragmentShadingRateCoverageSamples { nullptr } + , maxFragmentShadingRateRasterizationSamples { nullptr } + , fragmentShadingRateWithShaderDepthStencilWrites { nullptr } + , fragmentShadingRateWithSampleMask { nullptr } + , fragmentShadingRateWithShaderSampleMask { nullptr } + , fragmentShadingRateWithConservativeRasterization { nullptr } + , fragmentShadingRateWithFragmentShaderInterlock { nullptr } + , fragmentShadingRateWithCustomSampleLocations { nullptr } + , fragmentShadingRateStrictMultiplyCombiner { nullptr } + , layeredApiCount { nullptr } + , pLayeredApis { nullptr } + , layerProperties { nullptr } + , robustFragmentShadingRateAttachmentAccess { nullptr } + , separateDepthStencilAttachmentAccess { nullptr } + , maxDescriptorSetTotalUniformBuffersDynamic { nullptr } + , maxDescriptorSetTotalStorageBuffersDynamic { nullptr } + , maxDescriptorSetTotalBuffersDynamic { nullptr } + , maxDescriptorSetUpdateAfterBindTotalUniformBuffersDynamic { nullptr } + , maxDescriptorSetUpdateAfterBindTotalStorageBuffersDynamic { nullptr } + , maxDescriptorSetUpdateAfterBindTotalBuffersDynamic { nullptr } + , image2DViewOf3DSparse { nullptr } + , defaultVertexAttributeValue { nullptr } + , rgba4OpaqueBlackSwizzled { nullptr } + , resolveSrgbFormatAppliesTransferFunction { nullptr } + , resolveSrgbFormatSupportsTransferFunctionControl { nullptr } + , allowCommandBufferQueryCopies { nullptr } + , pipelineBinaryInternalCache { nullptr } + , pipelineBinaryInternalCacheControl { nullptr } + , pipelineBinaryPrefersInternalCache { nullptr } + , pipelineBinaryPrecompiledInternalCache { nullptr } + , pipelineBinaryCompressedData { nullptr } + , pipelineExecutableInfo { nullptr } + , shaderGroupHandleSize { nullptr } + , maxRayRecursionDepth { nullptr } + , maxShaderGroupStride { nullptr } + , shaderGroupBaseAlignment { nullptr } + , shaderGroupHandleCaptureReplaySize { nullptr } + , maxRayDispatchInvocationCount { nullptr } + , shaderGroupHandleAlignment { nullptr } + , maxRayHitAttributeSize { nullptr } + , robustStorageBufferAccessSizeAlignment { nullptr } + , robustUniformBufferAccessSizeAlignment { nullptr } { + + _clear(); + _link(); + } + + device_properties_khr(const device_properties_khr& properties) + : VkPhysicalDeviceAccelerationStructurePropertiesKHR { properties } + , VkPhysicalDeviceComputeShaderDerivativesPropertiesKHR { properties } + , VkPhysicalDeviceCooperativeMatrixPropertiesKHR { properties } + , VkPhysicalDeviceCopyMemoryIndirectPropertiesKHR { properties } + , VkPhysicalDeviceFragmentShaderBarycentricPropertiesKHR { properties } + , VkPhysicalDeviceFragmentShadingRatePropertiesKHR { properties } + , VkPhysicalDeviceLayeredApiPropertiesListKHR { properties } + , VkPhysicalDeviceLayeredApiVulkanPropertiesKHR { properties } + , VkPhysicalDeviceMaintenance7PropertiesKHR { properties } + , VkPhysicalDeviceMaintenance9PropertiesKHR { properties } + , VkPhysicalDeviceMaintenance10PropertiesKHR { properties } + , VkPhysicalDevicePerformanceQueryPropertiesKHR { properties } + , VkPhysicalDevicePipelineBinaryPropertiesKHR { properties } + , VkPhysicalDevicePipelineExecutablePropertiesFeaturesKHR { properties } + , VkPhysicalDeviceRayTracingPipelinePropertiesKHR { properties } + , VkPhysicalDeviceRobustness2PropertiesKHR { properties } + , maxGeometryCount { nullptr } + , maxInstanceCount { nullptr } + , maxPrimitiveCount { nullptr } + , maxPerStageDescriptorAccelerationStructures { nullptr } + , maxPerStageDescriptorUpdateAfterBindAccelerationStructures { nullptr } + , maxDescriptorSetAccelerationStructures { nullptr } + , maxDescriptorSetUpdateAfterBindAccelerationStructures { nullptr } + , minAccelerationStructureScratchOffsetAlignment { nullptr } + , meshAndTaskShaderDerivatives { nullptr } + , cooperativeMatrixSupportedStages { nullptr } + , supportedCopyQueues { nullptr } + , triStripVertexOrderIndependentOfProvokingVertex { nullptr } + , minFragmentShadingRateAttachmentTexelSize { nullptr } + , maxFragmentShadingRateAttachmentTexelSize { nullptr } + , maxFragmentShadingRateAttachmentTexelSizeAspectRatio { nullptr } + , primitiveFragmentShadingRateWithMultipleViewports { nullptr } + , layeredShadingRateAttachments { nullptr } + , fragmentShadingRateNonTrivialCombinerOps { nullptr } + , maxFragmentSize { nullptr } + , maxFragmentSizeAspectRatio { nullptr } + , maxFragmentShadingRateCoverageSamples { nullptr } + , maxFragmentShadingRateRasterizationSamples { nullptr } + , fragmentShadingRateWithShaderDepthStencilWrites { nullptr } + , fragmentShadingRateWithSampleMask { nullptr } + , fragmentShadingRateWithShaderSampleMask { nullptr } + , fragmentShadingRateWithConservativeRasterization { nullptr } + , fragmentShadingRateWithFragmentShaderInterlock { nullptr } + , fragmentShadingRateWithCustomSampleLocations { nullptr } + , fragmentShadingRateStrictMultiplyCombiner { nullptr } + , layeredApiCount { nullptr } + , pLayeredApis { nullptr } + , layerProperties { nullptr } + , robustFragmentShadingRateAttachmentAccess { nullptr } + , separateDepthStencilAttachmentAccess { nullptr } + , maxDescriptorSetTotalUniformBuffersDynamic { nullptr } + , maxDescriptorSetTotalStorageBuffersDynamic { nullptr } + , maxDescriptorSetTotalBuffersDynamic { nullptr } + , maxDescriptorSetUpdateAfterBindTotalUniformBuffersDynamic { nullptr } + , maxDescriptorSetUpdateAfterBindTotalStorageBuffersDynamic { nullptr } + , maxDescriptorSetUpdateAfterBindTotalBuffersDynamic { nullptr } + , image2DViewOf3DSparse { nullptr } + , defaultVertexAttributeValue { nullptr } + , rgba4OpaqueBlackSwizzled { nullptr } + , resolveSrgbFormatAppliesTransferFunction { nullptr } + , resolveSrgbFormatSupportsTransferFunctionControl { nullptr } + , allowCommandBufferQueryCopies { nullptr } + , pipelineBinaryInternalCache { nullptr } + , pipelineBinaryInternalCacheControl { nullptr } + , pipelineBinaryPrefersInternalCache { nullptr } + , pipelineBinaryPrecompiledInternalCache { nullptr } + , pipelineBinaryCompressedData { nullptr } + , pipelineExecutableInfo { nullptr } + , shaderGroupHandleSize { nullptr } + , maxRayRecursionDepth { nullptr } + , maxShaderGroupStride { nullptr } + , shaderGroupBaseAlignment { nullptr } + , shaderGroupHandleCaptureReplaySize { nullptr } + , maxRayDispatchInvocationCount { nullptr } + , shaderGroupHandleAlignment { nullptr } + , maxRayHitAttributeSize { nullptr } + , robustStorageBufferAccessSizeAlignment { nullptr } + , robustUniformBufferAccessSizeAlignment { nullptr } { + + _link(); + } + + device_properties_khr& operator=(const device_properties_khr& properties) { + + VkPhysicalDeviceAccelerationStructurePropertiesKHR::operator=(properties); + VkPhysicalDeviceComputeShaderDerivativesPropertiesKHR::operator=(properties); + VkPhysicalDeviceCooperativeMatrixPropertiesKHR::operator=(properties); + VkPhysicalDeviceCopyMemoryIndirectPropertiesKHR::operator=(properties); + VkPhysicalDeviceFragmentShaderBarycentricPropertiesKHR::operator=(properties); + VkPhysicalDeviceFragmentShadingRatePropertiesKHR::operator=(properties); + VkPhysicalDeviceLayeredApiPropertiesListKHR::operator=(properties); + VkPhysicalDeviceLayeredApiVulkanPropertiesKHR::operator=(properties); + VkPhysicalDeviceMaintenance7PropertiesKHR::operator=(properties); + VkPhysicalDeviceMaintenance9PropertiesKHR::operator=(properties); + VkPhysicalDeviceMaintenance10PropertiesKHR::operator=(properties); + VkPhysicalDevicePerformanceQueryPropertiesKHR::operator=(properties); + VkPhysicalDevicePipelineBinaryPropertiesKHR::operator=(properties); + VkPhysicalDevicePipelineExecutablePropertiesFeaturesKHR::operator=(properties); + VkPhysicalDeviceRayTracingPipelinePropertiesKHR::operator=(properties); + VkPhysicalDeviceRobustness2PropertiesKHR::operator=(properties); + + _link(); + + return *this; + } + + /// + /// \brief Chain an extension structure + /// \param next + void chain(void* next) { + + VkPhysicalDeviceRobustness2PropertiesKHR::pNext = next; + } + + /// + /// \brief Implicit casting for chaining + operator void*() { + + return static_cast(this); + } + + +// Helpers ------------------------------------------------------------------------------------------------------------- +private: + + void _clear() { + + // Clear out the struct + fennec::memset(this, 0, sizeof(*this)); + + // Set the structure types + VkPhysicalDeviceAccelerationStructurePropertiesKHR::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_ACCELERATION_STRUCTURE_PROPERTIES_KHR; + VkPhysicalDeviceComputeShaderDerivativesPropertiesKHR::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_COMPUTE_SHADER_DERIVATIVES_PROPERTIES_KHR; + VkPhysicalDeviceCooperativeMatrixPropertiesKHR::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_COOPERATIVE_MATRIX_PROPERTIES_KHR; + VkPhysicalDeviceCopyMemoryIndirectPropertiesKHR::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_COPY_MEMORY_INDIRECT_PROPERTIES_KHR; + VkPhysicalDeviceFragmentShaderBarycentricPropertiesKHR::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_FRAGMENT_SHADER_BARYCENTRIC_PROPERTIES_KHR; + VkPhysicalDeviceFragmentShadingRatePropertiesKHR::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_FRAGMENT_SHADING_RATE_PROPERTIES_KHR; + } + + void _link() { + + // Link to Extension Structures + maxGeometryCount = &(VkPhysicalDeviceAccelerationStructurePropertiesKHR::maxGeometryCount); + maxInstanceCount = &(VkPhysicalDeviceAccelerationStructurePropertiesKHR::maxInstanceCount); + maxPrimitiveCount = &(VkPhysicalDeviceAccelerationStructurePropertiesKHR::maxPrimitiveCount); + maxPerStageDescriptorAccelerationStructures = &(VkPhysicalDeviceAccelerationStructurePropertiesKHR::maxPerStageDescriptorAccelerationStructures); + maxPerStageDescriptorUpdateAfterBindAccelerationStructures = &(VkPhysicalDeviceAccelerationStructurePropertiesKHR::maxPerStageDescriptorUpdateAfterBindAccelerationStructures); + maxDescriptorSetAccelerationStructures = &(VkPhysicalDeviceAccelerationStructurePropertiesKHR::maxDescriptorSetAccelerationStructures); + maxDescriptorSetUpdateAfterBindAccelerationStructures = &(VkPhysicalDeviceAccelerationStructurePropertiesKHR::maxDescriptorSetUpdateAfterBindAccelerationStructures); + minAccelerationStructureScratchOffsetAlignment = &(VkPhysicalDeviceAccelerationStructurePropertiesKHR::minAccelerationStructureScratchOffsetAlignment); + meshAndTaskShaderDerivatives = &(VkPhysicalDeviceComputeShaderDerivativesPropertiesKHR::meshAndTaskShaderDerivatives); + cooperativeMatrixSupportedStages = &(VkPhysicalDeviceCooperativeMatrixPropertiesKHR::cooperativeMatrixSupportedStages); + supportedCopyQueues = &(VkPhysicalDeviceCopyMemoryIndirectPropertiesKHR::supportedQueues); + triStripVertexOrderIndependentOfProvokingVertex = &(VkPhysicalDeviceFragmentShaderBarycentricPropertiesKHR::triStripVertexOrderIndependentOfProvokingVertex); + minFragmentShadingRateAttachmentTexelSize = &(VkPhysicalDeviceFragmentShadingRatePropertiesKHR::minFragmentShadingRateAttachmentTexelSize); + maxFragmentShadingRateAttachmentTexelSize = &(VkPhysicalDeviceFragmentShadingRatePropertiesKHR::maxFragmentShadingRateAttachmentTexelSize); + maxFragmentShadingRateAttachmentTexelSizeAspectRatio = &(VkPhysicalDeviceFragmentShadingRatePropertiesKHR::maxFragmentShadingRateAttachmentTexelSizeAspectRatio); + primitiveFragmentShadingRateWithMultipleViewports = &(VkPhysicalDeviceFragmentShadingRatePropertiesKHR::primitiveFragmentShadingRateWithMultipleViewports); + layeredShadingRateAttachments = &(VkPhysicalDeviceFragmentShadingRatePropertiesKHR::layeredShadingRateAttachments); + fragmentShadingRateNonTrivialCombinerOps = &(VkPhysicalDeviceFragmentShadingRatePropertiesKHR::fragmentShadingRateNonTrivialCombinerOps); + maxFragmentSize = &(VkPhysicalDeviceFragmentShadingRatePropertiesKHR::maxFragmentSize); + maxFragmentSizeAspectRatio = &(VkPhysicalDeviceFragmentShadingRatePropertiesKHR::maxFragmentSizeAspectRatio); + maxFragmentShadingRateCoverageSamples = &(VkPhysicalDeviceFragmentShadingRatePropertiesKHR::maxFragmentShadingRateCoverageSamples); + maxFragmentShadingRateRasterizationSamples = &(VkPhysicalDeviceFragmentShadingRatePropertiesKHR::maxFragmentShadingRateRasterizationSamples); + fragmentShadingRateWithShaderDepthStencilWrites = &(VkPhysicalDeviceFragmentShadingRatePropertiesKHR::fragmentShadingRateWithShaderDepthStencilWrites); + fragmentShadingRateWithSampleMask = &(VkPhysicalDeviceFragmentShadingRatePropertiesKHR::fragmentShadingRateWithSampleMask); + fragmentShadingRateWithShaderSampleMask = &(VkPhysicalDeviceFragmentShadingRatePropertiesKHR::fragmentShadingRateWithShaderSampleMask); + fragmentShadingRateWithConservativeRasterization = &(VkPhysicalDeviceFragmentShadingRatePropertiesKHR::fragmentShadingRateWithConservativeRasterization); + fragmentShadingRateWithFragmentShaderInterlock = &(VkPhysicalDeviceFragmentShadingRatePropertiesKHR::fragmentShadingRateWithFragmentShaderInterlock); + fragmentShadingRateWithCustomSampleLocations = &(VkPhysicalDeviceFragmentShadingRatePropertiesKHR::fragmentShadingRateWithCustomSampleLocations); + fragmentShadingRateStrictMultiplyCombiner = &(VkPhysicalDeviceFragmentShadingRatePropertiesKHR::fragmentShadingRateStrictMultiplyCombiner); + layeredApiCount = &(VkPhysicalDeviceLayeredApiPropertiesListKHR::layeredApiCount); + pLayeredApis = &(VkPhysicalDeviceLayeredApiPropertiesListKHR::pLayeredApis); + layerProperties = &(VkPhysicalDeviceLayeredApiVulkanPropertiesKHR::properties); + robustFragmentShadingRateAttachmentAccess = &(VkPhysicalDeviceMaintenance7PropertiesKHR::robustFragmentShadingRateAttachmentAccess); + separateDepthStencilAttachmentAccess = &(VkPhysicalDeviceMaintenance7PropertiesKHR::separateDepthStencilAttachmentAccess); + maxDescriptorSetTotalUniformBuffersDynamic = &(VkPhysicalDeviceMaintenance7PropertiesKHR::maxDescriptorSetTotalUniformBuffersDynamic); + maxDescriptorSetTotalStorageBuffersDynamic = &(VkPhysicalDeviceMaintenance7PropertiesKHR::maxDescriptorSetTotalStorageBuffersDynamic); + maxDescriptorSetTotalBuffersDynamic = &(VkPhysicalDeviceMaintenance7PropertiesKHR::maxDescriptorSetTotalBuffersDynamic); + maxDescriptorSetUpdateAfterBindTotalUniformBuffersDynamic = &(VkPhysicalDeviceMaintenance7PropertiesKHR::maxDescriptorSetUpdateAfterBindTotalUniformBuffersDynamic); + maxDescriptorSetUpdateAfterBindTotalStorageBuffersDynamic = &(VkPhysicalDeviceMaintenance7PropertiesKHR::maxDescriptorSetUpdateAfterBindTotalStorageBuffersDynamic); + maxDescriptorSetUpdateAfterBindTotalBuffersDynamic = &(VkPhysicalDeviceMaintenance7PropertiesKHR::maxDescriptorSetUpdateAfterBindTotalBuffersDynamic); + image2DViewOf3DSparse = &(VkPhysicalDeviceMaintenance9PropertiesKHR::image2DViewOf3DSparse); + defaultVertexAttributeValue = &(VkPhysicalDeviceMaintenance9PropertiesKHR::defaultVertexAttributeValue); + rgba4OpaqueBlackSwizzled = &(VkPhysicalDeviceMaintenance10PropertiesKHR::rgba4OpaqueBlackSwizzled); + resolveSrgbFormatAppliesTransferFunction = &(VkPhysicalDeviceMaintenance10PropertiesKHR::resolveSrgbFormatAppliesTransferFunction); + resolveSrgbFormatSupportsTransferFunctionControl = &(VkPhysicalDeviceMaintenance10PropertiesKHR::resolveSrgbFormatSupportsTransferFunctionControl); + allowCommandBufferQueryCopies = &(VkPhysicalDevicePerformanceQueryPropertiesKHR::allowCommandBufferQueryCopies); + pipelineBinaryInternalCache = &(VkPhysicalDevicePipelineBinaryPropertiesKHR::pipelineBinaryInternalCache); + pipelineBinaryInternalCacheControl = &(VkPhysicalDevicePipelineBinaryPropertiesKHR::pipelineBinaryInternalCacheControl); + pipelineBinaryPrefersInternalCache = &(VkPhysicalDevicePipelineBinaryPropertiesKHR::pipelineBinaryPrefersInternalCache); + pipelineBinaryPrecompiledInternalCache = &(VkPhysicalDevicePipelineBinaryPropertiesKHR::pipelineBinaryPrecompiledInternalCache); + pipelineBinaryCompressedData = &(VkPhysicalDevicePipelineBinaryPropertiesKHR::pipelineBinaryCompressedData); + pipelineExecutableInfo = &(VkPhysicalDevicePipelineExecutablePropertiesFeaturesKHR::pipelineExecutableInfo); + shaderGroupHandleSize = &(VkPhysicalDeviceRayTracingPipelinePropertiesKHR::shaderGroupHandleSize); + maxRayRecursionDepth = &(VkPhysicalDeviceRayTracingPipelinePropertiesKHR::maxRayRecursionDepth); + maxShaderGroupStride = &(VkPhysicalDeviceRayTracingPipelinePropertiesKHR::maxShaderGroupStride); + shaderGroupBaseAlignment = &(VkPhysicalDeviceRayTracingPipelinePropertiesKHR::shaderGroupBaseAlignment); + shaderGroupHandleCaptureReplaySize = &(VkPhysicalDeviceRayTracingPipelinePropertiesKHR::shaderGroupHandleCaptureReplaySize); + maxRayDispatchInvocationCount = &(VkPhysicalDeviceRayTracingPipelinePropertiesKHR::maxRayDispatchInvocationCount); + shaderGroupHandleAlignment = &(VkPhysicalDeviceRayTracingPipelinePropertiesKHR::shaderGroupHandleAlignment); + maxRayHitAttributeSize = &(VkPhysicalDeviceRayTracingPipelinePropertiesKHR::maxRayHitAttributeSize); + robustStorageBufferAccessSizeAlignment = &(VkPhysicalDeviceRobustness2PropertiesKHR::robustStorageBufferAccessSizeAlignment); + robustUniformBufferAccessSizeAlignment = &(VkPhysicalDeviceRobustness2PropertiesKHR::robustUniformBufferAccessSizeAlignment); + + // Daisy chain + VkPhysicalDeviceAccelerationStructurePropertiesKHR::pNext = static_cast(this); + VkPhysicalDeviceComputeShaderDerivativesPropertiesKHR::pNext = static_cast(this); + VkPhysicalDeviceCooperativeMatrixPropertiesKHR::pNext = static_cast(this); + VkPhysicalDeviceCopyMemoryIndirectPropertiesKHR::pNext = static_cast(this); + VkPhysicalDeviceFragmentShaderBarycentricPropertiesKHR::pNext = static_cast(this); + VkPhysicalDeviceFragmentShadingRatePropertiesKHR::pNext = static_cast(this); + VkPhysicalDeviceLayeredApiPropertiesListKHR::pNext = static_cast(this); + VkPhysicalDeviceLayeredApiVulkanPropertiesKHR::pNext = static_cast(this); + VkPhysicalDeviceMaintenance7PropertiesKHR::pNext = static_cast(this); + VkPhysicalDeviceMaintenance9PropertiesKHR::pNext = static_cast(this); + VkPhysicalDeviceMaintenance10PropertiesKHR::pNext = static_cast(this); + VkPhysicalDevicePerformanceQueryPropertiesKHR::pNext = static_cast(this); + VkPhysicalDevicePipelineBinaryPropertiesKHR::pNext = static_cast(this); + VkPhysicalDevicePipelineExecutablePropertiesFeaturesKHR::pNext = static_cast(this); + VkPhysicalDeviceRayTracingPipelinePropertiesKHR::pNext = static_cast(this); + VkPhysicalDeviceRobustness2PropertiesKHR::pNext = nullptr; + } +}; + +/// +/// \brief EXT Properties +struct device_properties_ext : private VkPhysicalDeviceBlendOperationAdvancedPropertiesEXT, + private VkPhysicalDeviceConservativeRasterizationPropertiesEXT, + private VkPhysicalDeviceCustomBorderColorPropertiesEXT, + private VkPhysicalDeviceDescriptorBufferDensityMapPropertiesEXT, + private VkPhysicalDeviceDescriptorBufferPropertiesEXT, + private VkPhysicalDeviceDeviceGeneratedCommandsPropertiesEXT, + private VkPhysicalDeviceDiscardRectanglePropertiesEXT, + private VkPhysicalDeviceDrmPropertiesEXT, + private VkPhysicalDeviceExtendedDynamicState3PropertiesEXT, + private VkPhysicalDeviceExternalMemoryHostPropertiesEXT, + private VkPhysicalDeviceFragmentDensityMapPropertiesEXT, + private VkPhysicalDeviceFragmentDensityMap2PropertiesEXT, + private VkPhysicalDeviceFragmentDensityMapOffsetPropertiesEXT, + private VkPhysicalDeviceGraphicsPipelineLibraryPropertiesEXT, + private VkPhysicalDeviceLegacyVertexAttributesPropertiesEXT, + private VkPhysicalDeviceMapMemoryPlacedPropertiesEXT, + private VkPhysicalDeviceMemoryBudgetPropertiesEXT, + private VkPhysicalDeviceMemoryDecompressionPropertiesEXT, + private VkPhysicalDeviceMeshShaderPropertiesEXT, + private VkPhysicalDeviceMultiDrawPropertiesEXT, + private VkPhysicalDeviceNestedCommandBufferPropertiesEXT, + private VkPhysicalDeviceOpacityMicromapPropertiesEXT, + private VkPhysicalDevicePCIBusInfoPropertiesEXT, + private VkPhysicalDevicePipelinePropertiesFeaturesEXT, + private VkPhysicalDeviceProvokingVertexPropertiesEXT, + private VkPhysicalDeviceRayTracingInvocationReorderPropertiesEXT, + private VkPhysicalDeviceSampleLocationsPropertiesEXT, + private VkPhysicalDeviceShaderObjectPropertiesEXT, + private VkPhysicalDeviceShaderTileImagePropertiesEXT, + private VkPhysicalDeviceTransformFeedbackPropertiesEXT, + private VkPhysicalDeviceVertexAttributeDivisorPropertiesEXT { + +// Public References --------------------------------------------------------------------------------------------------- +public: + + /// \name Properties + /// @{ + + uint32_t* advancedBlendMaxColorAttachments; + VkBool32* advancedBlendIndependentBlend; + VkBool32* advancedBlendNonPremultipliedSrcColor; + VkBool32* advancedBlendNonPremultipliedDstColor; + VkBool32* advancedBlendCorrelatedOverlap; + VkBool32* advancedBlendAllOperations; + float* primitiveOverestimationSize; + float* maxExtraPrimitiveOverestimationSize; + float* extraPrimitiveOverestimationSizeGranularity; + VkBool32* primitiveUnderestimation; + VkBool32* conservativePointAndLineRasterization; + VkBool32* degenerateTrianglesRasterized; + VkBool32* degenerateLinesRasterized; + VkBool32* fullyCoveredFragmentShaderInputVariable; + VkBool32* conservativeRasterizationPostDepthCoverage; + uint32_t* maxCustomBorderColorSamplers; + size_t* combinedImageSamplerDensityMapDescriptorSize; + VkBool32* combinedImageSamplerDescriptorSingleArray; + VkBool32* bufferlessPushDescriptors; + VkBool32* allowSamplerImageViewPostSubmitCreation; + VkDeviceSize* descriptorBufferOffsetAlignment; + uint32_t* maxDescriptorBufferBindings; + uint32_t* maxResourceDescriptorBufferBindings; + uint32_t* maxSamplerDescriptorBufferBindings; + uint32_t* maxEmbeddedImmutableSamplerBindings; + uint32_t* maxEmbeddedImmutableSamplers; + size_t* bufferCaptureReplayDescriptorDataSize; + size_t* imageCaptureReplayDescriptorDataSize; + size_t* imageViewCaptureReplayDescriptorDataSize; + size_t* samplerCaptureReplayDescriptorDataSize; + size_t* accelerationStructureCaptureReplayDescriptorDataSize; + size_t* samplerDescriptorSize; + size_t* combinedImageSamplerDescriptorSize; + size_t* sampledImageDescriptorSize; + size_t* storageImageDescriptorSize; + size_t* uniformTexelBufferDescriptorSize; + size_t* robustUniformTexelBufferDescriptorSize; + size_t* storageTexelBufferDescriptorSize; + size_t* robustStorageTexelBufferDescriptorSize; + size_t* uniformBufferDescriptorSize; + size_t* robustUniformBufferDescriptorSize; + size_t* storageBufferDescriptorSize; + size_t* robustStorageBufferDescriptorSize; + size_t* inputAttachmentDescriptorSize; + size_t* accelerationStructureDescriptorSize; + VkDeviceSize* maxSamplerDescriptorBufferRange; + VkDeviceSize* maxResourceDescriptorBufferRange; + VkDeviceSize* samplerDescriptorBufferAddressSpaceSize; + VkDeviceSize* resourceDescriptorBufferAddressSpaceSize; + VkDeviceSize* descriptorBufferAddressSpaceSize; + uint32_t* maxIndirectPipelineCount; + uint32_t* maxIndirectShaderObjectCount; + uint32_t* maxIndirectSequenceCount; + uint32_t* maxIndirectCommandsTokenCount; + uint32_t* maxIndirectCommandsTokenOffset; + uint32_t* maxIndirectCommandsIndirectStride; + VkIndirectCommandsInputModeFlagsEXT* supportedIndirectCommandsInputModes; + VkShaderStageFlags* supportedIndirectCommandsShaderStages; + VkShaderStageFlags* supportedIndirectCommandsShaderStagesPipelineBinding; + VkShaderStageFlags* supportedIndirectCommandsShaderStagesShaderBinding; + VkBool32* deviceGeneratedCommandsTransformFeedback; + VkBool32* deviceGeneratedCommandsMultiDrawIndirectCount; + uint32_t* maxDiscardRectangles; + VkBool32* hasPrimary; + VkBool32* hasRender; + int64_t* primaryMajor; + int64_t* primaryMinor; + int64_t* renderMajor; + int64_t* renderMinor; + VkBool32* dynamicPrimitiveTopologyUnrestricted; + VkDeviceSize* minImportedHostPointerAlignment; + VkExtent2D* minFragmentDensityTexelSize; + VkExtent2D* maxFragmentDensityTexelSize; + VkBool32* fragmentDensityInvocations; + VkBool32* subsampledLoads; + VkBool32* subsampledCoarseReconstructionEarlyAccess; + uint32_t* maxSubsampledArrayLayers; + uint32_t* maxDescriptorSetSubsampledSamplers; + VkExtent2D* fragmentDensityOffsetGranularity; + VkBool32* graphicsPipelineLibraryFastLinking; + VkBool32* graphicsPipelineLibraryIndependentInterpolationDecoration; + VkBool32* nativeUnalignedPerformance; + VkDeviceSize* minPlacedMemoryMapAlignment; + VkDeviceSize (*heapBudget)[VK_MAX_MEMORY_HEAPS]; + VkDeviceSize (*heapUsage)[VK_MAX_MEMORY_HEAPS]; + VkMemoryDecompressionMethodFlagsEXT* decompressionMethods; + uint64_t* maxDecompressionIndirectCount; + uint32_t* maxTaskWorkGroupTotalCount; + uint32_t (*maxTaskWorkGroupCount)[3]; + uint32_t* maxTaskWorkGroupInvocations; + uint32_t (*maxTaskWorkGroupSize)[3]; + uint32_t* maxTaskPayloadSize; + uint32_t* maxTaskSharedMemorySize; + uint32_t* maxTaskPayloadAndSharedMemorySize; + uint32_t* maxMeshWorkGroupTotalCount; + uint32_t (*maxMeshWorkGroupCount)[3]; + uint32_t* maxMeshWorkGroupInvocations; + uint32_t (*maxMeshWorkGroupSize)[3]; + uint32_t* maxMeshSharedMemorySize; + uint32_t* maxMeshPayloadAndSharedMemorySize; + uint32_t* maxMeshOutputMemorySize; + uint32_t* maxMeshPayloadAndOutputMemorySize; + uint32_t* maxMeshOutputComponents; + uint32_t* maxMeshOutputVertices; + uint32_t* maxMeshOutputPrimitives; + uint32_t* maxMeshOutputLayers; + uint32_t* maxMeshMultiviewViewCount; + uint32_t* meshOutputPerVertexGranularity; + uint32_t* meshOutputPerPrimitiveGranularity; + uint32_t* maxPreferredTaskWorkGroupInvocations; + uint32_t* maxPreferredMeshWorkGroupInvocations; + VkBool32* prefersLocalInvocationVertexOutput; + VkBool32* prefersLocalInvocationPrimitiveOutput; + VkBool32* prefersCompactVertexOutput; + VkBool32* prefersCompactPrimitiveOutput; + uint32_t* maxMultiDrawCount; + uint32_t* maxCommandBufferNestingLevel; + uint32_t* maxOpacity2StateSubdivisionLevel; + uint32_t* maxOpacity4StateSubdivisionLevel; + uint32_t* pciDomain; + uint32_t* pciBus; + uint32_t* pciDevice; + uint32_t* pciFunction; + VkBool32* pipelinePropertiesIdentifier; + VkBool32* provokingVertexModePerPipeline; + VkBool32* transformFeedbackPreservesTriangleFanProvokingVertex; + VkRayTracingInvocationReorderModeEXT* rayTracingInvocationReorderReorderingHint; + uint32_t* maxShaderBindingTableRecordIndex; + VkSampleCountFlags* sampleLocationSampleCounts; + VkExtent2D* maxSampleLocationGridSize; + float (*sampleLocationCoordinateRange)[2]; + uint32_t* sampleLocationSubPixelBits; + VkBool32* variableSampleLocations; + uint8_t (*shaderBinaryUUID)[VK_UUID_SIZE]; + uint32_t* shaderBinaryVersion; + VkBool32* shaderTileImageCoherentReadAccelerated; + VkBool32* shaderTileImageReadSampleFromPixelRateInvocation; + VkBool32* shaderTileImageReadFromHelperInvocation; + uint32_t* maxTransformFeedbackStreams; + uint32_t* maxTransformFeedbackBuffers; + VkDeviceSize* maxTransformFeedbackBufferSize; + uint32_t* maxTransformFeedbackStreamDataSize; + uint32_t* maxTransformFeedbackBufferDataSize; + uint32_t* maxTransformFeedbackBufferDataStride; + VkBool32* transformFeedbackQueries; + VkBool32* transformFeedbackStreamsLinesTriangles; + VkBool32* transformFeedbackRasterizationStreamSelect; + VkBool32* transformFeedbackDraw; + uint32_t* maxVertexAttribDivisor; + + /// @} + + +// Methods ------------------------------------------------------------------------------------------------------------- +public: + + device_properties_ext() + : VkPhysicalDeviceBlendOperationAdvancedPropertiesEXT { } + , VkPhysicalDeviceConservativeRasterizationPropertiesEXT { } + , VkPhysicalDeviceCustomBorderColorPropertiesEXT { } + , VkPhysicalDeviceDescriptorBufferDensityMapPropertiesEXT { } + , VkPhysicalDeviceDescriptorBufferPropertiesEXT { } + , VkPhysicalDeviceDeviceGeneratedCommandsPropertiesEXT { } + , VkPhysicalDeviceDiscardRectanglePropertiesEXT { } + , VkPhysicalDeviceDrmPropertiesEXT { } + , VkPhysicalDeviceExtendedDynamicState3PropertiesEXT { } + , VkPhysicalDeviceExternalMemoryHostPropertiesEXT { } + , VkPhysicalDeviceFragmentDensityMapPropertiesEXT { } + , VkPhysicalDeviceFragmentDensityMap2PropertiesEXT { } + , VkPhysicalDeviceFragmentDensityMapOffsetPropertiesEXT { } + , VkPhysicalDeviceGraphicsPipelineLibraryPropertiesEXT { } + , VkPhysicalDeviceLegacyVertexAttributesPropertiesEXT { } + , VkPhysicalDeviceMapMemoryPlacedPropertiesEXT { } + , VkPhysicalDeviceMemoryBudgetPropertiesEXT { } + , VkPhysicalDeviceMemoryDecompressionPropertiesEXT { } + , VkPhysicalDeviceMeshShaderPropertiesEXT { } + , VkPhysicalDeviceMultiDrawPropertiesEXT { } + , VkPhysicalDeviceNestedCommandBufferPropertiesEXT { } + , VkPhysicalDeviceOpacityMicromapPropertiesEXT { } + , VkPhysicalDevicePCIBusInfoPropertiesEXT { } + , VkPhysicalDevicePipelinePropertiesFeaturesEXT { } + , VkPhysicalDeviceProvokingVertexPropertiesEXT { } + , VkPhysicalDeviceRayTracingInvocationReorderPropertiesEXT { } + , VkPhysicalDeviceSampleLocationsPropertiesEXT { } + , VkPhysicalDeviceShaderObjectPropertiesEXT { } + , VkPhysicalDeviceShaderTileImagePropertiesEXT { } + , VkPhysicalDeviceTransformFeedbackPropertiesEXT { } + , VkPhysicalDeviceVertexAttributeDivisorPropertiesEXT { } + , advancedBlendMaxColorAttachments { nullptr } + , advancedBlendIndependentBlend { nullptr } + , advancedBlendNonPremultipliedSrcColor { nullptr } + , advancedBlendNonPremultipliedDstColor { nullptr } + , advancedBlendCorrelatedOverlap { nullptr } + , advancedBlendAllOperations { nullptr } + , primitiveOverestimationSize { nullptr } + , maxExtraPrimitiveOverestimationSize { nullptr } + , extraPrimitiveOverestimationSizeGranularity { nullptr } + , primitiveUnderestimation { nullptr } + , conservativePointAndLineRasterization { nullptr } + , degenerateTrianglesRasterized { nullptr } + , degenerateLinesRasterized { nullptr } + , fullyCoveredFragmentShaderInputVariable { nullptr } + , conservativeRasterizationPostDepthCoverage { nullptr } + , maxCustomBorderColorSamplers { nullptr } + , combinedImageSamplerDensityMapDescriptorSize { nullptr } + , combinedImageSamplerDescriptorSingleArray { nullptr } + , bufferlessPushDescriptors { nullptr } + , allowSamplerImageViewPostSubmitCreation { nullptr } + , descriptorBufferOffsetAlignment { nullptr } + , maxDescriptorBufferBindings { nullptr } + , maxResourceDescriptorBufferBindings { nullptr } + , maxSamplerDescriptorBufferBindings { nullptr } + , maxEmbeddedImmutableSamplerBindings { nullptr } + , maxEmbeddedImmutableSamplers { nullptr } + , bufferCaptureReplayDescriptorDataSize { nullptr } + , imageCaptureReplayDescriptorDataSize { nullptr } + , imageViewCaptureReplayDescriptorDataSize { nullptr } + , samplerCaptureReplayDescriptorDataSize { nullptr } + , accelerationStructureCaptureReplayDescriptorDataSize { nullptr } + , samplerDescriptorSize { nullptr } + , combinedImageSamplerDescriptorSize { nullptr } + , sampledImageDescriptorSize { nullptr } + , storageImageDescriptorSize { nullptr } + , uniformTexelBufferDescriptorSize { nullptr } + , robustUniformTexelBufferDescriptorSize { nullptr } + , storageTexelBufferDescriptorSize { nullptr } + , robustStorageTexelBufferDescriptorSize { nullptr } + , uniformBufferDescriptorSize { nullptr } + , robustUniformBufferDescriptorSize { nullptr } + , storageBufferDescriptorSize { nullptr } + , robustStorageBufferDescriptorSize { nullptr } + , inputAttachmentDescriptorSize { nullptr } + , accelerationStructureDescriptorSize { nullptr } + , maxSamplerDescriptorBufferRange { nullptr } + , maxResourceDescriptorBufferRange { nullptr } + , samplerDescriptorBufferAddressSpaceSize { nullptr } + , resourceDescriptorBufferAddressSpaceSize { nullptr } + , descriptorBufferAddressSpaceSize { nullptr } + , maxIndirectPipelineCount { nullptr } + , maxIndirectShaderObjectCount { nullptr } + , maxIndirectSequenceCount { nullptr } + , maxIndirectCommandsTokenCount { nullptr } + , maxIndirectCommandsTokenOffset { nullptr } + , maxIndirectCommandsIndirectStride { nullptr } + , supportedIndirectCommandsInputModes { nullptr } + , supportedIndirectCommandsShaderStages { nullptr } + , supportedIndirectCommandsShaderStagesPipelineBinding { nullptr } + , supportedIndirectCommandsShaderStagesShaderBinding { nullptr } + , deviceGeneratedCommandsTransformFeedback { nullptr } + , deviceGeneratedCommandsMultiDrawIndirectCount { nullptr } + , maxDiscardRectangles { nullptr } + , hasPrimary { nullptr } + , hasRender { nullptr } + , primaryMajor { nullptr } + , primaryMinor { nullptr } + , renderMajor { nullptr } + , renderMinor { nullptr } + , dynamicPrimitiveTopologyUnrestricted { nullptr } + , minImportedHostPointerAlignment { nullptr } + , minFragmentDensityTexelSize { nullptr } + , maxFragmentDensityTexelSize { nullptr } + , fragmentDensityInvocations { nullptr } + , subsampledLoads { nullptr } + , subsampledCoarseReconstructionEarlyAccess { nullptr } + , maxSubsampledArrayLayers { nullptr } + , maxDescriptorSetSubsampledSamplers { nullptr } + , fragmentDensityOffsetGranularity { nullptr } + , graphicsPipelineLibraryFastLinking { nullptr } + , graphicsPipelineLibraryIndependentInterpolationDecoration { nullptr } + , nativeUnalignedPerformance { nullptr } + , minPlacedMemoryMapAlignment { nullptr } + , heapBudget { nullptr } + , heapUsage { nullptr } + , decompressionMethods { nullptr } + , maxDecompressionIndirectCount { nullptr } + , maxTaskWorkGroupTotalCount { nullptr } + , maxTaskWorkGroupCount { nullptr } + , maxTaskWorkGroupInvocations { nullptr } + , maxTaskWorkGroupSize { nullptr } + , maxTaskPayloadSize { nullptr } + , maxTaskSharedMemorySize { nullptr } + , maxTaskPayloadAndSharedMemorySize { nullptr } + , maxMeshWorkGroupTotalCount { nullptr } + , maxMeshWorkGroupCount { nullptr } + , maxMeshWorkGroupInvocations { nullptr } + , maxMeshWorkGroupSize { nullptr } + , maxMeshSharedMemorySize { nullptr } + , maxMeshPayloadAndSharedMemorySize { nullptr } + , maxMeshOutputMemorySize { nullptr } + , maxMeshPayloadAndOutputMemorySize { nullptr } + , maxMeshOutputComponents { nullptr } + , maxMeshOutputVertices { nullptr } + , maxMeshOutputPrimitives { nullptr } + , maxMeshOutputLayers { nullptr } + , maxMeshMultiviewViewCount { nullptr } + , meshOutputPerVertexGranularity { nullptr } + , meshOutputPerPrimitiveGranularity { nullptr } + , maxPreferredTaskWorkGroupInvocations { nullptr } + , maxPreferredMeshWorkGroupInvocations { nullptr } + , prefersLocalInvocationVertexOutput { nullptr } + , prefersLocalInvocationPrimitiveOutput { nullptr } + , prefersCompactVertexOutput { nullptr } + , prefersCompactPrimitiveOutput { nullptr } + , maxMultiDrawCount { nullptr } + , maxCommandBufferNestingLevel { nullptr } + , maxOpacity2StateSubdivisionLevel { nullptr } + , maxOpacity4StateSubdivisionLevel { nullptr } + , pciDomain { nullptr } + , pciBus { nullptr } + , pciDevice { nullptr } + , pciFunction { nullptr } + , pipelinePropertiesIdentifier { nullptr } + , provokingVertexModePerPipeline { nullptr } + , transformFeedbackPreservesTriangleFanProvokingVertex { nullptr } + , rayTracingInvocationReorderReorderingHint { nullptr } + , maxShaderBindingTableRecordIndex { nullptr } + , sampleLocationSampleCounts { nullptr } + , maxSampleLocationGridSize { nullptr } + , sampleLocationCoordinateRange { nullptr } + , sampleLocationSubPixelBits { nullptr } + , variableSampleLocations { nullptr } + , shaderBinaryUUID { nullptr } + , shaderBinaryVersion { nullptr } + , shaderTileImageCoherentReadAccelerated { nullptr } + , shaderTileImageReadSampleFromPixelRateInvocation { nullptr } + , shaderTileImageReadFromHelperInvocation { nullptr } + , maxTransformFeedbackStreams { nullptr } + , maxTransformFeedbackBuffers { nullptr } + , maxTransformFeedbackBufferSize { nullptr } + , maxTransformFeedbackStreamDataSize { nullptr } + , maxTransformFeedbackBufferDataSize { nullptr } + , maxTransformFeedbackBufferDataStride { nullptr } + , transformFeedbackQueries { nullptr } + , transformFeedbackStreamsLinesTriangles { nullptr } + , transformFeedbackRasterizationStreamSelect { nullptr } + , transformFeedbackDraw { nullptr } + , maxVertexAttribDivisor { nullptr } { + + _clear(); + _link(); + } + + device_properties_ext(const device_properties_ext& properties) + : VkPhysicalDeviceBlendOperationAdvancedPropertiesEXT { properties } + , VkPhysicalDeviceConservativeRasterizationPropertiesEXT { properties } + , VkPhysicalDeviceCustomBorderColorPropertiesEXT { properties } + , VkPhysicalDeviceDescriptorBufferDensityMapPropertiesEXT { properties } + , VkPhysicalDeviceDescriptorBufferPropertiesEXT { properties } + , VkPhysicalDeviceDeviceGeneratedCommandsPropertiesEXT { properties } + , VkPhysicalDeviceDiscardRectanglePropertiesEXT { properties } + , VkPhysicalDeviceDrmPropertiesEXT { properties } + , VkPhysicalDeviceExtendedDynamicState3PropertiesEXT { properties } + , VkPhysicalDeviceExternalMemoryHostPropertiesEXT { properties } + , VkPhysicalDeviceFragmentDensityMapPropertiesEXT { properties } + , VkPhysicalDeviceFragmentDensityMap2PropertiesEXT { properties } + , VkPhysicalDeviceFragmentDensityMapOffsetPropertiesEXT { properties } + , VkPhysicalDeviceGraphicsPipelineLibraryPropertiesEXT { properties } + , VkPhysicalDeviceLegacyVertexAttributesPropertiesEXT { properties } + , VkPhysicalDeviceMapMemoryPlacedPropertiesEXT { properties } + , VkPhysicalDeviceMemoryBudgetPropertiesEXT { properties } + , VkPhysicalDeviceMemoryDecompressionPropertiesEXT { properties } + , VkPhysicalDeviceMeshShaderPropertiesEXT { properties } + , VkPhysicalDeviceMultiDrawPropertiesEXT { properties } + , VkPhysicalDeviceNestedCommandBufferPropertiesEXT { properties } + , VkPhysicalDeviceOpacityMicromapPropertiesEXT { properties } + , VkPhysicalDevicePCIBusInfoPropertiesEXT { properties } + , VkPhysicalDevicePipelinePropertiesFeaturesEXT { properties } + , VkPhysicalDeviceProvokingVertexPropertiesEXT { properties } + , VkPhysicalDeviceRayTracingInvocationReorderPropertiesEXT { properties } + , VkPhysicalDeviceSampleLocationsPropertiesEXT { properties } + , VkPhysicalDeviceShaderObjectPropertiesEXT { properties } + , VkPhysicalDeviceShaderTileImagePropertiesEXT { properties } + , VkPhysicalDeviceTransformFeedbackPropertiesEXT { properties } + , VkPhysicalDeviceVertexAttributeDivisorPropertiesEXT { properties } + , advancedBlendMaxColorAttachments { nullptr } + , advancedBlendIndependentBlend { nullptr } + , advancedBlendNonPremultipliedSrcColor { nullptr } + , advancedBlendNonPremultipliedDstColor { nullptr } + , advancedBlendCorrelatedOverlap { nullptr } + , advancedBlendAllOperations { nullptr } + , primitiveOverestimationSize { nullptr } + , maxExtraPrimitiveOverestimationSize { nullptr } + , extraPrimitiveOverestimationSizeGranularity { nullptr } + , primitiveUnderestimation { nullptr } + , conservativePointAndLineRasterization { nullptr } + , degenerateTrianglesRasterized { nullptr } + , degenerateLinesRasterized { nullptr } + , fullyCoveredFragmentShaderInputVariable { nullptr } + , conservativeRasterizationPostDepthCoverage { nullptr } + , maxCustomBorderColorSamplers { nullptr } + , combinedImageSamplerDensityMapDescriptorSize { nullptr } + , combinedImageSamplerDescriptorSingleArray { nullptr } + , bufferlessPushDescriptors { nullptr } + , allowSamplerImageViewPostSubmitCreation { nullptr } + , descriptorBufferOffsetAlignment { nullptr } + , maxDescriptorBufferBindings { nullptr } + , maxResourceDescriptorBufferBindings { nullptr } + , maxSamplerDescriptorBufferBindings { nullptr } + , maxEmbeddedImmutableSamplerBindings { nullptr } + , maxEmbeddedImmutableSamplers { nullptr } + , bufferCaptureReplayDescriptorDataSize { nullptr } + , imageCaptureReplayDescriptorDataSize { nullptr } + , imageViewCaptureReplayDescriptorDataSize { nullptr } + , samplerCaptureReplayDescriptorDataSize { nullptr } + , accelerationStructureCaptureReplayDescriptorDataSize { nullptr } + , samplerDescriptorSize { nullptr } + , combinedImageSamplerDescriptorSize { nullptr } + , sampledImageDescriptorSize { nullptr } + , storageImageDescriptorSize { nullptr } + , uniformTexelBufferDescriptorSize { nullptr } + , robustUniformTexelBufferDescriptorSize { nullptr } + , storageTexelBufferDescriptorSize { nullptr } + , robustStorageTexelBufferDescriptorSize { nullptr } + , uniformBufferDescriptorSize { nullptr } + , robustUniformBufferDescriptorSize { nullptr } + , storageBufferDescriptorSize { nullptr } + , robustStorageBufferDescriptorSize { nullptr } + , inputAttachmentDescriptorSize { nullptr } + , accelerationStructureDescriptorSize { nullptr } + , maxSamplerDescriptorBufferRange { nullptr } + , maxResourceDescriptorBufferRange { nullptr } + , samplerDescriptorBufferAddressSpaceSize { nullptr } + , resourceDescriptorBufferAddressSpaceSize { nullptr } + , descriptorBufferAddressSpaceSize { nullptr } + , maxIndirectPipelineCount { nullptr } + , maxIndirectShaderObjectCount { nullptr } + , maxIndirectSequenceCount { nullptr } + , maxIndirectCommandsTokenCount { nullptr } + , maxIndirectCommandsTokenOffset { nullptr } + , maxIndirectCommandsIndirectStride { nullptr } + , supportedIndirectCommandsInputModes { nullptr } + , supportedIndirectCommandsShaderStages { nullptr } + , supportedIndirectCommandsShaderStagesPipelineBinding { nullptr } + , supportedIndirectCommandsShaderStagesShaderBinding { nullptr } + , deviceGeneratedCommandsTransformFeedback { nullptr } + , deviceGeneratedCommandsMultiDrawIndirectCount { nullptr } + , maxDiscardRectangles { nullptr } + , hasPrimary { nullptr } + , hasRender { nullptr } + , primaryMajor { nullptr } + , primaryMinor { nullptr } + , renderMajor { nullptr } + , renderMinor { nullptr } + , dynamicPrimitiveTopologyUnrestricted { nullptr } + , minImportedHostPointerAlignment { nullptr } + , minFragmentDensityTexelSize { nullptr } + , maxFragmentDensityTexelSize { nullptr } + , fragmentDensityInvocations { nullptr } + , subsampledLoads { nullptr } + , subsampledCoarseReconstructionEarlyAccess { nullptr } + , maxSubsampledArrayLayers { nullptr } + , maxDescriptorSetSubsampledSamplers { nullptr } + , fragmentDensityOffsetGranularity { nullptr } + , graphicsPipelineLibraryFastLinking { nullptr } + , graphicsPipelineLibraryIndependentInterpolationDecoration { nullptr } + , nativeUnalignedPerformance { nullptr } + , minPlacedMemoryMapAlignment { nullptr } + , heapBudget { nullptr } + , heapUsage { nullptr } + , decompressionMethods { nullptr } + , maxDecompressionIndirectCount { nullptr } + , maxTaskWorkGroupTotalCount { nullptr } + , maxTaskWorkGroupCount { nullptr } + , maxTaskWorkGroupInvocations { nullptr } + , maxTaskWorkGroupSize { nullptr } + , maxTaskPayloadSize { nullptr } + , maxTaskSharedMemorySize { nullptr } + , maxTaskPayloadAndSharedMemorySize { nullptr } + , maxMeshWorkGroupTotalCount { nullptr } + , maxMeshWorkGroupCount { nullptr } + , maxMeshWorkGroupInvocations { nullptr } + , maxMeshWorkGroupSize { nullptr } + , maxMeshSharedMemorySize { nullptr } + , maxMeshPayloadAndSharedMemorySize { nullptr } + , maxMeshOutputMemorySize { nullptr } + , maxMeshPayloadAndOutputMemorySize { nullptr } + , maxMeshOutputComponents { nullptr } + , maxMeshOutputVertices { nullptr } + , maxMeshOutputPrimitives { nullptr } + , maxMeshOutputLayers { nullptr } + , maxMeshMultiviewViewCount { nullptr } + , meshOutputPerVertexGranularity { nullptr } + , meshOutputPerPrimitiveGranularity { nullptr } + , maxPreferredTaskWorkGroupInvocations { nullptr } + , maxPreferredMeshWorkGroupInvocations { nullptr } + , prefersLocalInvocationVertexOutput { nullptr } + , prefersLocalInvocationPrimitiveOutput { nullptr } + , prefersCompactVertexOutput { nullptr } + , prefersCompactPrimitiveOutput { nullptr } + , maxMultiDrawCount { nullptr } + , maxCommandBufferNestingLevel { nullptr } + , maxOpacity2StateSubdivisionLevel { nullptr } + , maxOpacity4StateSubdivisionLevel { nullptr } + , pciDomain { nullptr } + , pciBus { nullptr } + , pciDevice { nullptr } + , pciFunction { nullptr } + , pipelinePropertiesIdentifier { nullptr } + , provokingVertexModePerPipeline { nullptr } + , transformFeedbackPreservesTriangleFanProvokingVertex { nullptr } + , rayTracingInvocationReorderReorderingHint { nullptr } + , maxShaderBindingTableRecordIndex { nullptr } + , sampleLocationSampleCounts { nullptr } + , maxSampleLocationGridSize { nullptr } + , sampleLocationCoordinateRange { nullptr } + , sampleLocationSubPixelBits { nullptr } + , variableSampleLocations { nullptr } + , shaderBinaryUUID { nullptr } + , shaderBinaryVersion { nullptr } + , shaderTileImageCoherentReadAccelerated { nullptr } + , shaderTileImageReadSampleFromPixelRateInvocation { nullptr } + , shaderTileImageReadFromHelperInvocation { nullptr } + , maxTransformFeedbackStreams { nullptr } + , maxTransformFeedbackBuffers { nullptr } + , maxTransformFeedbackBufferSize { nullptr } + , maxTransformFeedbackStreamDataSize { nullptr } + , maxTransformFeedbackBufferDataSize { nullptr } + , maxTransformFeedbackBufferDataStride { nullptr } + , transformFeedbackQueries { nullptr } + , transformFeedbackStreamsLinesTriangles { nullptr } + , transformFeedbackRasterizationStreamSelect { nullptr } + , transformFeedbackDraw { nullptr } + , maxVertexAttribDivisor { nullptr } { + + _link(); + } + + device_properties_ext& operator=(const device_properties_ext& properties) { + if (&properties == this) { + return *this; + } + + VkPhysicalDeviceBlendOperationAdvancedPropertiesEXT::operator=(properties); + VkPhysicalDeviceConservativeRasterizationPropertiesEXT::operator=(properties); + VkPhysicalDeviceCustomBorderColorPropertiesEXT::operator=(properties); + VkPhysicalDeviceDescriptorBufferDensityMapPropertiesEXT::operator=(properties); + VkPhysicalDeviceDescriptorBufferPropertiesEXT::operator=(properties); + VkPhysicalDeviceDeviceGeneratedCommandsPropertiesEXT::operator=(properties); + VkPhysicalDeviceDiscardRectanglePropertiesEXT::operator=(properties); + VkPhysicalDeviceDrmPropertiesEXT::operator=(properties); + VkPhysicalDeviceExtendedDynamicState3PropertiesEXT::operator=(properties); + VkPhysicalDeviceExternalMemoryHostPropertiesEXT::operator=(properties); + VkPhysicalDeviceFragmentDensityMapPropertiesEXT::operator=(properties); + VkPhysicalDeviceFragmentDensityMap2PropertiesEXT::operator=(properties); + VkPhysicalDeviceFragmentDensityMapOffsetPropertiesEXT::operator=(properties); + VkPhysicalDeviceGraphicsPipelineLibraryPropertiesEXT::operator=(properties); + VkPhysicalDeviceLegacyVertexAttributesPropertiesEXT::operator=(properties); + VkPhysicalDeviceMapMemoryPlacedPropertiesEXT::operator=(properties); + VkPhysicalDeviceMemoryBudgetPropertiesEXT::operator=(properties); + VkPhysicalDeviceMemoryDecompressionPropertiesEXT::operator=(properties); + VkPhysicalDeviceMeshShaderPropertiesEXT::operator=(properties); + VkPhysicalDeviceMultiDrawPropertiesEXT::operator=(properties); + VkPhysicalDeviceNestedCommandBufferPropertiesEXT::operator=(properties); + VkPhysicalDeviceOpacityMicromapPropertiesEXT::operator=(properties); + VkPhysicalDevicePCIBusInfoPropertiesEXT::operator=(properties); + VkPhysicalDevicePipelinePropertiesFeaturesEXT::operator=(properties); + VkPhysicalDeviceProvokingVertexPropertiesEXT::operator=(properties); + VkPhysicalDeviceRayTracingInvocationReorderPropertiesEXT::operator=(properties); + VkPhysicalDeviceSampleLocationsPropertiesEXT::operator=(properties); + VkPhysicalDeviceShaderObjectPropertiesEXT::operator=(properties); + VkPhysicalDeviceShaderTileImagePropertiesEXT::operator=(properties); + VkPhysicalDeviceTransformFeedbackPropertiesEXT::operator=(properties); + VkPhysicalDeviceVertexAttributeDivisorPropertiesEXT::operator=(properties); + + _link(); + + return *this; + } + + +// Helpers ------------------------------------------------------------------------------------------------------------- +private: + + void _clear() { + + // Clear out the structure + fennec::memset(this, 0, sizeof(*this)); + + // Set the structure types + VkPhysicalDeviceBlendOperationAdvancedPropertiesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_BLEND_OPERATION_ADVANCED_PROPERTIES_EXT; + VkPhysicalDeviceConservativeRasterizationPropertiesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_CONSERVATIVE_RASTERIZATION_PROPERTIES_EXT; + VkPhysicalDeviceCustomBorderColorPropertiesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_CUSTOM_BORDER_COLOR_PROPERTIES_EXT; + VkPhysicalDeviceDescriptorBufferDensityMapPropertiesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_DESCRIPTOR_BUFFER_DENSITY_MAP_PROPERTIES_EXT; + VkPhysicalDeviceDescriptorBufferPropertiesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_DESCRIPTOR_BUFFER_PROPERTIES_EXT; + VkPhysicalDeviceDeviceGeneratedCommandsPropertiesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_DEVICE_GENERATED_COMMANDS_PROPERTIES_EXT; + VkPhysicalDeviceDiscardRectanglePropertiesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_DISCARD_RECTANGLE_PROPERTIES_EXT; + VkPhysicalDeviceDrmPropertiesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_DRM_PROPERTIES_EXT; + VkPhysicalDeviceExtendedDynamicState3PropertiesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_EXTENDED_DYNAMIC_STATE_3_PROPERTIES_EXT; + VkPhysicalDeviceExternalMemoryHostPropertiesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_EXTERNAL_MEMORY_HOST_PROPERTIES_EXT; + VkPhysicalDeviceFragmentDensityMapPropertiesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_FRAGMENT_DENSITY_MAP_PROPERTIES_EXT; + VkPhysicalDeviceFragmentDensityMap2PropertiesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_FRAGMENT_DENSITY_MAP_2_PROPERTIES_EXT; + VkPhysicalDeviceFragmentDensityMapOffsetPropertiesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_FRAGMENT_DENSITY_MAP_OFFSET_PROPERTIES_EXT; + VkPhysicalDeviceGraphicsPipelineLibraryPropertiesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_GRAPHICS_PIPELINE_LIBRARY_PROPERTIES_EXT; + VkPhysicalDeviceLegacyVertexAttributesPropertiesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_LEGACY_VERTEX_ATTRIBUTES_PROPERTIES_EXT; + VkPhysicalDeviceMapMemoryPlacedPropertiesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_MAP_MEMORY_PLACED_PROPERTIES_EXT; + VkPhysicalDeviceMemoryBudgetPropertiesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_MEMORY_BUDGET_PROPERTIES_EXT; + VkPhysicalDeviceMemoryDecompressionPropertiesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_MEMORY_DECOMPRESSION_PROPERTIES_EXT; + VkPhysicalDeviceMeshShaderPropertiesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_MESH_SHADER_PROPERTIES_EXT; + VkPhysicalDeviceMultiDrawPropertiesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_MULTI_DRAW_PROPERTIES_EXT; + VkPhysicalDeviceNestedCommandBufferPropertiesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_NESTED_COMMAND_BUFFER_PROPERTIES_EXT; + VkPhysicalDeviceOpacityMicromapPropertiesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_OPACITY_MICROMAP_PROPERTIES_EXT; + VkPhysicalDevicePCIBusInfoPropertiesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_PCI_BUS_INFO_PROPERTIES_EXT; + VkPhysicalDevicePipelinePropertiesFeaturesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_PIPELINE_PROPERTIES_FEATURES_EXT; + VkPhysicalDeviceProvokingVertexPropertiesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_PROVOKING_VERTEX_PROPERTIES_EXT; + VkPhysicalDeviceRayTracingInvocationReorderPropertiesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_RAY_TRACING_INVOCATION_REORDER_PROPERTIES_EXT; + VkPhysicalDeviceSampleLocationsPropertiesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SAMPLE_LOCATIONS_PROPERTIES_EXT; + VkPhysicalDeviceShaderObjectPropertiesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SHADER_OBJECT_PROPERTIES_EXT; + VkPhysicalDeviceShaderTileImagePropertiesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_SHADER_TILE_IMAGE_PROPERTIES_EXT; + VkPhysicalDeviceTransformFeedbackPropertiesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_TRANSFORM_FEEDBACK_PROPERTIES_EXT; + VkPhysicalDeviceVertexAttributeDivisorPropertiesEXT::sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_VERTEX_ATTRIBUTE_DIVISOR_PROPERTIES_EXT; + } + + void _link() { + + // Link to extension structures + advancedBlendMaxColorAttachments = &(VkPhysicalDeviceBlendOperationAdvancedPropertiesEXT::advancedBlendMaxColorAttachments); + advancedBlendIndependentBlend = &(VkPhysicalDeviceBlendOperationAdvancedPropertiesEXT::advancedBlendIndependentBlend); + advancedBlendNonPremultipliedSrcColor = &(VkPhysicalDeviceBlendOperationAdvancedPropertiesEXT::advancedBlendNonPremultipliedSrcColor); + advancedBlendNonPremultipliedDstColor = &(VkPhysicalDeviceBlendOperationAdvancedPropertiesEXT::advancedBlendNonPremultipliedDstColor); + advancedBlendCorrelatedOverlap = &(VkPhysicalDeviceBlendOperationAdvancedPropertiesEXT::advancedBlendCorrelatedOverlap); + advancedBlendAllOperations = &(VkPhysicalDeviceBlendOperationAdvancedPropertiesEXT::advancedBlendAllOperations); + primitiveOverestimationSize = &(VkPhysicalDeviceConservativeRasterizationPropertiesEXT::primitiveOverestimationSize); + maxExtraPrimitiveOverestimationSize = &(VkPhysicalDeviceConservativeRasterizationPropertiesEXT::maxExtraPrimitiveOverestimationSize); + extraPrimitiveOverestimationSizeGranularity = &(VkPhysicalDeviceConservativeRasterizationPropertiesEXT::extraPrimitiveOverestimationSizeGranularity); + primitiveUnderestimation = &(VkPhysicalDeviceConservativeRasterizationPropertiesEXT::primitiveUnderestimation); + conservativePointAndLineRasterization = &(VkPhysicalDeviceConservativeRasterizationPropertiesEXT::conservativePointAndLineRasterization); + degenerateTrianglesRasterized = &(VkPhysicalDeviceConservativeRasterizationPropertiesEXT::degenerateTrianglesRasterized); + degenerateLinesRasterized = &(VkPhysicalDeviceConservativeRasterizationPropertiesEXT::degenerateLinesRasterized); + fullyCoveredFragmentShaderInputVariable = &(VkPhysicalDeviceConservativeRasterizationPropertiesEXT::fullyCoveredFragmentShaderInputVariable); + conservativeRasterizationPostDepthCoverage = &(VkPhysicalDeviceConservativeRasterizationPropertiesEXT::conservativeRasterizationPostDepthCoverage); + maxCustomBorderColorSamplers = &(VkPhysicalDeviceCustomBorderColorPropertiesEXT::maxCustomBorderColorSamplers); + combinedImageSamplerDensityMapDescriptorSize = &(VkPhysicalDeviceDescriptorBufferDensityMapPropertiesEXT::combinedImageSamplerDensityMapDescriptorSize); + combinedImageSamplerDescriptorSingleArray = &(VkPhysicalDeviceDescriptorBufferPropertiesEXT::combinedImageSamplerDescriptorSingleArray); + bufferlessPushDescriptors = &(VkPhysicalDeviceDescriptorBufferPropertiesEXT::bufferlessPushDescriptors); + allowSamplerImageViewPostSubmitCreation = &(VkPhysicalDeviceDescriptorBufferPropertiesEXT::allowSamplerImageViewPostSubmitCreation); + descriptorBufferOffsetAlignment = &(VkPhysicalDeviceDescriptorBufferPropertiesEXT::descriptorBufferOffsetAlignment); + maxDescriptorBufferBindings = &(VkPhysicalDeviceDescriptorBufferPropertiesEXT::maxDescriptorBufferBindings); + maxResourceDescriptorBufferBindings = &(VkPhysicalDeviceDescriptorBufferPropertiesEXT::maxResourceDescriptorBufferBindings); + maxSamplerDescriptorBufferBindings = &(VkPhysicalDeviceDescriptorBufferPropertiesEXT::maxSamplerDescriptorBufferBindings); + maxEmbeddedImmutableSamplerBindings = &(VkPhysicalDeviceDescriptorBufferPropertiesEXT::maxEmbeddedImmutableSamplerBindings); + maxEmbeddedImmutableSamplers = &(VkPhysicalDeviceDescriptorBufferPropertiesEXT::maxEmbeddedImmutableSamplers); + bufferCaptureReplayDescriptorDataSize = &(VkPhysicalDeviceDescriptorBufferPropertiesEXT::bufferCaptureReplayDescriptorDataSize); + imageCaptureReplayDescriptorDataSize = &(VkPhysicalDeviceDescriptorBufferPropertiesEXT::imageCaptureReplayDescriptorDataSize); + imageViewCaptureReplayDescriptorDataSize = &(VkPhysicalDeviceDescriptorBufferPropertiesEXT::imageViewCaptureReplayDescriptorDataSize); + samplerCaptureReplayDescriptorDataSize = &(VkPhysicalDeviceDescriptorBufferPropertiesEXT::samplerCaptureReplayDescriptorDataSize); + accelerationStructureCaptureReplayDescriptorDataSize = &(VkPhysicalDeviceDescriptorBufferPropertiesEXT::accelerationStructureCaptureReplayDescriptorDataSize); + samplerDescriptorSize = &(VkPhysicalDeviceDescriptorBufferPropertiesEXT::samplerDescriptorSize); + combinedImageSamplerDescriptorSize = &(VkPhysicalDeviceDescriptorBufferPropertiesEXT::combinedImageSamplerDescriptorSize); + sampledImageDescriptorSize = &(VkPhysicalDeviceDescriptorBufferPropertiesEXT::sampledImageDescriptorSize); + storageImageDescriptorSize = &(VkPhysicalDeviceDescriptorBufferPropertiesEXT::storageImageDescriptorSize); + uniformTexelBufferDescriptorSize = &(VkPhysicalDeviceDescriptorBufferPropertiesEXT::uniformTexelBufferDescriptorSize); + robustUniformTexelBufferDescriptorSize = &(VkPhysicalDeviceDescriptorBufferPropertiesEXT::robustUniformTexelBufferDescriptorSize); + storageTexelBufferDescriptorSize = &(VkPhysicalDeviceDescriptorBufferPropertiesEXT::storageTexelBufferDescriptorSize); + robustStorageTexelBufferDescriptorSize = &(VkPhysicalDeviceDescriptorBufferPropertiesEXT::robustStorageTexelBufferDescriptorSize); + uniformBufferDescriptorSize = &(VkPhysicalDeviceDescriptorBufferPropertiesEXT::uniformBufferDescriptorSize); + robustUniformBufferDescriptorSize = &(VkPhysicalDeviceDescriptorBufferPropertiesEXT::robustUniformBufferDescriptorSize); + storageBufferDescriptorSize = &(VkPhysicalDeviceDescriptorBufferPropertiesEXT::storageBufferDescriptorSize); + robustStorageBufferDescriptorSize = &(VkPhysicalDeviceDescriptorBufferPropertiesEXT::robustStorageBufferDescriptorSize); + inputAttachmentDescriptorSize = &(VkPhysicalDeviceDescriptorBufferPropertiesEXT::inputAttachmentDescriptorSize); + accelerationStructureDescriptorSize = &(VkPhysicalDeviceDescriptorBufferPropertiesEXT::accelerationStructureDescriptorSize); + maxSamplerDescriptorBufferRange = &(VkPhysicalDeviceDescriptorBufferPropertiesEXT::maxSamplerDescriptorBufferRange); + maxResourceDescriptorBufferRange = &(VkPhysicalDeviceDescriptorBufferPropertiesEXT::maxResourceDescriptorBufferRange); + samplerDescriptorBufferAddressSpaceSize = &(VkPhysicalDeviceDescriptorBufferPropertiesEXT::samplerDescriptorBufferAddressSpaceSize); + resourceDescriptorBufferAddressSpaceSize = &(VkPhysicalDeviceDescriptorBufferPropertiesEXT::resourceDescriptorBufferAddressSpaceSize); + descriptorBufferAddressSpaceSize = &(VkPhysicalDeviceDescriptorBufferPropertiesEXT::descriptorBufferAddressSpaceSize); + maxIndirectPipelineCount = &(VkPhysicalDeviceDeviceGeneratedCommandsPropertiesEXT::maxIndirectPipelineCount); + maxIndirectShaderObjectCount = &(VkPhysicalDeviceDeviceGeneratedCommandsPropertiesEXT::maxIndirectShaderObjectCount); + maxIndirectSequenceCount = &(VkPhysicalDeviceDeviceGeneratedCommandsPropertiesEXT::maxIndirectSequenceCount); + maxIndirectCommandsTokenCount = &(VkPhysicalDeviceDeviceGeneratedCommandsPropertiesEXT::maxIndirectCommandsTokenCount); + maxIndirectCommandsTokenOffset = &(VkPhysicalDeviceDeviceGeneratedCommandsPropertiesEXT::maxIndirectCommandsTokenOffset); + maxIndirectCommandsIndirectStride = &(VkPhysicalDeviceDeviceGeneratedCommandsPropertiesEXT::maxIndirectCommandsIndirectStride); + supportedIndirectCommandsInputModes = &(VkPhysicalDeviceDeviceGeneratedCommandsPropertiesEXT::supportedIndirectCommandsInputModes); + supportedIndirectCommandsShaderStages = &(VkPhysicalDeviceDeviceGeneratedCommandsPropertiesEXT::supportedIndirectCommandsShaderStages); + supportedIndirectCommandsShaderStagesPipelineBinding = &(VkPhysicalDeviceDeviceGeneratedCommandsPropertiesEXT::supportedIndirectCommandsShaderStagesPipelineBinding); + supportedIndirectCommandsShaderStagesShaderBinding = &(VkPhysicalDeviceDeviceGeneratedCommandsPropertiesEXT::supportedIndirectCommandsShaderStagesShaderBinding); + deviceGeneratedCommandsTransformFeedback = &(VkPhysicalDeviceDeviceGeneratedCommandsPropertiesEXT::deviceGeneratedCommandsTransformFeedback); + deviceGeneratedCommandsMultiDrawIndirectCount = &(VkPhysicalDeviceDeviceGeneratedCommandsPropertiesEXT::deviceGeneratedCommandsMultiDrawIndirectCount); + maxDiscardRectangles = &(VkPhysicalDeviceDiscardRectanglePropertiesEXT::maxDiscardRectangles); + hasPrimary = &(VkPhysicalDeviceDrmPropertiesEXT::hasPrimary); + hasRender = &(VkPhysicalDeviceDrmPropertiesEXT::hasRender); + primaryMajor = &(VkPhysicalDeviceDrmPropertiesEXT::primaryMajor); + primaryMinor = &(VkPhysicalDeviceDrmPropertiesEXT::primaryMinor); + renderMajor = &(VkPhysicalDeviceDrmPropertiesEXT::renderMajor); + renderMinor = &(VkPhysicalDeviceDrmPropertiesEXT::renderMinor); + dynamicPrimitiveTopologyUnrestricted = &(VkPhysicalDeviceExtendedDynamicState3PropertiesEXT::dynamicPrimitiveTopologyUnrestricted); + minImportedHostPointerAlignment = &(VkPhysicalDeviceExternalMemoryHostPropertiesEXT::minImportedHostPointerAlignment); + minFragmentDensityTexelSize = &(VkPhysicalDeviceFragmentDensityMapPropertiesEXT::minFragmentDensityTexelSize); + maxFragmentDensityTexelSize = &(VkPhysicalDeviceFragmentDensityMapPropertiesEXT::maxFragmentDensityTexelSize); + fragmentDensityInvocations = &(VkPhysicalDeviceFragmentDensityMapPropertiesEXT::fragmentDensityInvocations); + subsampledLoads = &(VkPhysicalDeviceFragmentDensityMap2PropertiesEXT::subsampledLoads); + subsampledCoarseReconstructionEarlyAccess = &(VkPhysicalDeviceFragmentDensityMap2PropertiesEXT::subsampledCoarseReconstructionEarlyAccess); + maxSubsampledArrayLayers = &(VkPhysicalDeviceFragmentDensityMap2PropertiesEXT::maxSubsampledArrayLayers); + maxDescriptorSetSubsampledSamplers = &(VkPhysicalDeviceFragmentDensityMap2PropertiesEXT::maxDescriptorSetSubsampledSamplers); + fragmentDensityOffsetGranularity = &(VkPhysicalDeviceFragmentDensityMapOffsetPropertiesEXT::fragmentDensityOffsetGranularity); + graphicsPipelineLibraryFastLinking = &(VkPhysicalDeviceGraphicsPipelineLibraryPropertiesEXT::graphicsPipelineLibraryFastLinking); + graphicsPipelineLibraryIndependentInterpolationDecoration = &(VkPhysicalDeviceGraphicsPipelineLibraryPropertiesEXT::graphicsPipelineLibraryIndependentInterpolationDecoration); + nativeUnalignedPerformance = &(VkPhysicalDeviceLegacyVertexAttributesPropertiesEXT::nativeUnalignedPerformance); + minPlacedMemoryMapAlignment = &(VkPhysicalDeviceMapMemoryPlacedPropertiesEXT::minPlacedMemoryMapAlignment); + heapBudget = &(VkPhysicalDeviceMemoryBudgetPropertiesEXT::heapBudget); + heapUsage = &(VkPhysicalDeviceMemoryBudgetPropertiesEXT::heapUsage); + decompressionMethods = &(VkPhysicalDeviceMemoryDecompressionPropertiesEXT::decompressionMethods); + maxDecompressionIndirectCount = &(VkPhysicalDeviceMemoryDecompressionPropertiesEXT::maxDecompressionIndirectCount); + maxTaskWorkGroupTotalCount = &(VkPhysicalDeviceMeshShaderPropertiesEXT::maxTaskWorkGroupTotalCount); + maxTaskWorkGroupCount = &(VkPhysicalDeviceMeshShaderPropertiesEXT::maxTaskWorkGroupCount); + maxTaskWorkGroupInvocations = &(VkPhysicalDeviceMeshShaderPropertiesEXT::maxTaskWorkGroupInvocations); + maxTaskWorkGroupSize = &(VkPhysicalDeviceMeshShaderPropertiesEXT::maxTaskWorkGroupSize); + maxTaskPayloadSize = &(VkPhysicalDeviceMeshShaderPropertiesEXT::maxTaskPayloadSize); + maxTaskSharedMemorySize = &(VkPhysicalDeviceMeshShaderPropertiesEXT::maxTaskSharedMemorySize); + maxTaskPayloadAndSharedMemorySize = &(VkPhysicalDeviceMeshShaderPropertiesEXT::maxTaskPayloadAndSharedMemorySize); + maxMeshWorkGroupTotalCount = &(VkPhysicalDeviceMeshShaderPropertiesEXT::maxMeshWorkGroupTotalCount); + maxMeshWorkGroupCount = &(VkPhysicalDeviceMeshShaderPropertiesEXT::maxMeshWorkGroupCount); + maxMeshWorkGroupInvocations = &(VkPhysicalDeviceMeshShaderPropertiesEXT::maxMeshWorkGroupInvocations); + maxMeshWorkGroupSize = &(VkPhysicalDeviceMeshShaderPropertiesEXT::maxMeshWorkGroupSize); + maxMeshSharedMemorySize = &(VkPhysicalDeviceMeshShaderPropertiesEXT::maxMeshSharedMemorySize); + maxMeshPayloadAndSharedMemorySize = &(VkPhysicalDeviceMeshShaderPropertiesEXT::maxMeshPayloadAndSharedMemorySize); + maxMeshOutputMemorySize = &(VkPhysicalDeviceMeshShaderPropertiesEXT::maxMeshOutputMemorySize); + maxMeshPayloadAndOutputMemorySize = &(VkPhysicalDeviceMeshShaderPropertiesEXT::maxMeshPayloadAndOutputMemorySize); + maxMeshOutputComponents = &(VkPhysicalDeviceMeshShaderPropertiesEXT::maxMeshOutputComponents); + maxMeshOutputVertices = &(VkPhysicalDeviceMeshShaderPropertiesEXT::maxMeshOutputVertices); + maxMeshOutputPrimitives = &(VkPhysicalDeviceMeshShaderPropertiesEXT::maxMeshOutputPrimitives); + maxMeshOutputLayers = &(VkPhysicalDeviceMeshShaderPropertiesEXT::maxMeshOutputLayers); + maxMeshMultiviewViewCount = &(VkPhysicalDeviceMeshShaderPropertiesEXT::maxMeshMultiviewViewCount); + meshOutputPerVertexGranularity = &(VkPhysicalDeviceMeshShaderPropertiesEXT::meshOutputPerVertexGranularity); + meshOutputPerPrimitiveGranularity = &(VkPhysicalDeviceMeshShaderPropertiesEXT::meshOutputPerPrimitiveGranularity); + maxPreferredTaskWorkGroupInvocations = &(VkPhysicalDeviceMeshShaderPropertiesEXT::maxPreferredTaskWorkGroupInvocations); + maxPreferredMeshWorkGroupInvocations = &(VkPhysicalDeviceMeshShaderPropertiesEXT::maxPreferredMeshWorkGroupInvocations); + prefersLocalInvocationVertexOutput = &(VkPhysicalDeviceMeshShaderPropertiesEXT::prefersLocalInvocationVertexOutput); + prefersLocalInvocationPrimitiveOutput = &(VkPhysicalDeviceMeshShaderPropertiesEXT::prefersLocalInvocationPrimitiveOutput); + prefersCompactVertexOutput = &(VkPhysicalDeviceMeshShaderPropertiesEXT::prefersCompactVertexOutput); + prefersCompactPrimitiveOutput = &(VkPhysicalDeviceMeshShaderPropertiesEXT::prefersCompactPrimitiveOutput); + maxMultiDrawCount = &(VkPhysicalDeviceMultiDrawPropertiesEXT::maxMultiDrawCount); + maxCommandBufferNestingLevel = &(VkPhysicalDeviceNestedCommandBufferPropertiesEXT::maxCommandBufferNestingLevel); + maxOpacity2StateSubdivisionLevel = &(VkPhysicalDeviceOpacityMicromapPropertiesEXT::maxOpacity2StateSubdivisionLevel); + maxOpacity4StateSubdivisionLevel = &(VkPhysicalDeviceOpacityMicromapPropertiesEXT::maxOpacity4StateSubdivisionLevel); + pciDomain = &(VkPhysicalDevicePCIBusInfoPropertiesEXT::pciDomain); + pciBus = &(VkPhysicalDevicePCIBusInfoPropertiesEXT::pciBus); + pciDevice = &(VkPhysicalDevicePCIBusInfoPropertiesEXT::pciDevice); + pciFunction = &(VkPhysicalDevicePCIBusInfoPropertiesEXT::pciFunction); + pipelinePropertiesIdentifier = &(VkPhysicalDevicePipelinePropertiesFeaturesEXT::pipelinePropertiesIdentifier); + provokingVertexModePerPipeline = &(VkPhysicalDeviceProvokingVertexPropertiesEXT::provokingVertexModePerPipeline); + transformFeedbackPreservesTriangleFanProvokingVertex = &(VkPhysicalDeviceProvokingVertexPropertiesEXT::transformFeedbackPreservesTriangleFanProvokingVertex); + rayTracingInvocationReorderReorderingHint = &(VkPhysicalDeviceRayTracingInvocationReorderPropertiesEXT::rayTracingInvocationReorderReorderingHint); + maxShaderBindingTableRecordIndex = &(VkPhysicalDeviceRayTracingInvocationReorderPropertiesEXT::maxShaderBindingTableRecordIndex); + sampleLocationSampleCounts = &(VkPhysicalDeviceSampleLocationsPropertiesEXT::sampleLocationSampleCounts); + maxSampleLocationGridSize = &(VkPhysicalDeviceSampleLocationsPropertiesEXT::maxSampleLocationGridSize); + sampleLocationCoordinateRange = &(VkPhysicalDeviceSampleLocationsPropertiesEXT::sampleLocationCoordinateRange); + sampleLocationSubPixelBits = &(VkPhysicalDeviceSampleLocationsPropertiesEXT::sampleLocationSubPixelBits); + variableSampleLocations = &(VkPhysicalDeviceSampleLocationsPropertiesEXT::variableSampleLocations); + shaderBinaryUUID = &(VkPhysicalDeviceShaderObjectPropertiesEXT::shaderBinaryUUID); + shaderBinaryVersion = &(VkPhysicalDeviceShaderObjectPropertiesEXT::shaderBinaryVersion); + shaderTileImageCoherentReadAccelerated = &(VkPhysicalDeviceShaderTileImagePropertiesEXT::shaderTileImageCoherentReadAccelerated); + shaderTileImageReadSampleFromPixelRateInvocation = &(VkPhysicalDeviceShaderTileImagePropertiesEXT::shaderTileImageReadSampleFromPixelRateInvocation); + shaderTileImageReadFromHelperInvocation = &(VkPhysicalDeviceShaderTileImagePropertiesEXT::shaderTileImageReadFromHelperInvocation); + maxTransformFeedbackStreams = &(VkPhysicalDeviceTransformFeedbackPropertiesEXT::maxTransformFeedbackStreams); + maxTransformFeedbackBuffers = &(VkPhysicalDeviceTransformFeedbackPropertiesEXT::maxTransformFeedbackBuffers); + maxTransformFeedbackBufferSize = &(VkPhysicalDeviceTransformFeedbackPropertiesEXT::maxTransformFeedbackBufferSize); + maxTransformFeedbackStreamDataSize = &(VkPhysicalDeviceTransformFeedbackPropertiesEXT::maxTransformFeedbackStreamDataSize); + maxTransformFeedbackBufferDataSize = &(VkPhysicalDeviceTransformFeedbackPropertiesEXT::maxTransformFeedbackBufferDataSize); + maxTransformFeedbackBufferDataStride = &(VkPhysicalDeviceTransformFeedbackPropertiesEXT::maxTransformFeedbackBufferDataStride); + transformFeedbackQueries = &(VkPhysicalDeviceTransformFeedbackPropertiesEXT::transformFeedbackQueries); + transformFeedbackStreamsLinesTriangles = &(VkPhysicalDeviceTransformFeedbackPropertiesEXT::transformFeedbackStreamsLinesTriangles); + transformFeedbackRasterizationStreamSelect = &(VkPhysicalDeviceTransformFeedbackPropertiesEXT::transformFeedbackRasterizationStreamSelect); + transformFeedbackDraw = &(VkPhysicalDeviceTransformFeedbackPropertiesEXT::transformFeedbackDraw); + maxVertexAttribDivisor = &(VkPhysicalDeviceVertexAttributeDivisorPropertiesEXT::maxVertexAttribDivisor); + + // Daisy chain + VkPhysicalDeviceBlendOperationAdvancedPropertiesEXT::pNext = (static_cast(this)); + VkPhysicalDeviceConservativeRasterizationPropertiesEXT::pNext = (static_cast(this)); + VkPhysicalDeviceCustomBorderColorPropertiesEXT::pNext = (static_cast(this)); + VkPhysicalDeviceDescriptorBufferDensityMapPropertiesEXT::pNext = (static_cast(this)); + VkPhysicalDeviceDescriptorBufferPropertiesEXT::pNext = (static_cast(this)); + VkPhysicalDeviceDeviceGeneratedCommandsPropertiesEXT::pNext = (static_cast(this)); + VkPhysicalDeviceDiscardRectanglePropertiesEXT::pNext = (static_cast(this)); + VkPhysicalDeviceDrmPropertiesEXT::pNext = (static_cast(this)); + VkPhysicalDeviceExtendedDynamicState3PropertiesEXT::pNext = (static_cast(this)); + VkPhysicalDeviceExternalMemoryHostPropertiesEXT::pNext = (static_cast(this)); + VkPhysicalDeviceFragmentDensityMapPropertiesEXT::pNext = (static_cast(this)); + VkPhysicalDeviceFragmentDensityMap2PropertiesEXT::pNext = (static_cast(this)); + VkPhysicalDeviceFragmentDensityMapOffsetPropertiesEXT::pNext = (static_cast(this)); + VkPhysicalDeviceGraphicsPipelineLibraryPropertiesEXT::pNext = (static_cast(this)); + VkPhysicalDeviceLegacyVertexAttributesPropertiesEXT::pNext = (static_cast(this)); + VkPhysicalDeviceMapMemoryPlacedPropertiesEXT::pNext = (static_cast(this)); + VkPhysicalDeviceMemoryBudgetPropertiesEXT::pNext = (static_cast(this)); + VkPhysicalDeviceMemoryDecompressionPropertiesEXT::pNext = (static_cast(this)); + VkPhysicalDeviceMeshShaderPropertiesEXT::pNext = (static_cast(this)); + VkPhysicalDeviceMultiDrawPropertiesEXT::pNext = (static_cast(this)); + VkPhysicalDeviceNestedCommandBufferPropertiesEXT::pNext = (static_cast(this)); + VkPhysicalDeviceOpacityMicromapPropertiesEXT::pNext = (static_cast(this)); + VkPhysicalDevicePCIBusInfoPropertiesEXT::pNext = (static_cast(this)); + VkPhysicalDevicePipelinePropertiesFeaturesEXT::pNext = (static_cast(this)); + VkPhysicalDeviceProvokingVertexPropertiesEXT::pNext = (static_cast(this)); + VkPhysicalDeviceRayTracingInvocationReorderPropertiesEXT::pNext = (static_cast(this)); + VkPhysicalDeviceSampleLocationsPropertiesEXT::pNext = (static_cast(this)); + VkPhysicalDeviceShaderObjectPropertiesEXT::pNext = (static_cast(this)); + VkPhysicalDeviceShaderTileImagePropertiesEXT::pNext = (static_cast(this)); + VkPhysicalDeviceTransformFeedbackPropertiesEXT::pNext = (static_cast(this)); + VkPhysicalDeviceVertexAttributeDivisorPropertiesEXT::pNext = nullptr; + + } +}; + + +/// +/// \brief Struct representing the properties of a physical device. +struct device_properties : private VkPhysicalDeviceProperties2, + private VkPhysicalDeviceMemoryProperties2, + private device_properties_11, + private device_properties_12, + private device_properties_13, + private device_properties_14, + private device_properties_khr, + private device_properties_ext { + +// Constructors & Destructor ------------------------------------------------------------------------------------------- +public: + + VkPhysicalDeviceProperties* core10; + VkPhysicalDeviceMemoryProperties* memory; + + + /// \name Constructors & Destructor + /// @{ + + /// + /// \brief Device Constructor + /// \param device The device to acquire properties from + explicit device_properties(VkPhysicalDevice device) + : VkPhysicalDeviceProperties2 { + [&]() -> VkPhysicalDeviceProperties2 { // Disgusting trick to handle initialization order + vkGetPhysicalDeviceProperties(device, &(VkPhysicalDeviceProperties2::properties)); + return *static_cast(this); + }() + } + , device_properties_11(VkPhysicalDeviceProperties2::properties) + , device_properties_12(VkPhysicalDeviceProperties2::properties) + , device_properties_13(VkPhysicalDeviceProperties2::properties) + , device_properties_14(VkPhysicalDeviceProperties2::properties) + , core10(&(VkPhysicalDeviceProperties2::properties)) + , memory(&(VkPhysicalDeviceMemoryProperties2::memoryProperties)) { + + // Acquire all properties after Core 1.0 if available + if (vkGetPhysicalDeviceProperties2) { + vkGetPhysicalDeviceProperties2(device, this); + } + + + // + if (vkGetPhysicalDeviceMemoryProperties2) { + vkGetPhysicalDeviceMemoryProperties2(device, this); + } else { + vkGetPhysicalDeviceMemoryProperties(device, &(VkPhysicalDeviceMemoryProperties2::memoryProperties)); + } + } + + device_properties(const device_properties& props) + : VkPhysicalDeviceProperties2 { props } + , device_properties_11(props) + , device_properties_12(props) + , device_properties_13(props) + , device_properties_14(props) + , device_properties_khr(props) + , device_properties_ext(props) + , core10(&(VkPhysicalDeviceProperties2::properties)) { + } + + device_properties& operator=(const device_properties& props) { + if (&props == this) { + return *this; + } + + VkPhysicalDeviceProperties2::operator=(props); + VkPhysicalDeviceProperties2::operator=(props); + VkPhysicalDeviceProperties2::operator=(props); + VkPhysicalDeviceProperties2::operator=(props); + VkPhysicalDeviceProperties2::operator=(props); + VkPhysicalDeviceProperties2::operator=(props); + VkPhysicalDeviceProperties2::operator=(props); + + return *this; + } + + /// @} +}; + +} + +#endif // FENNEC_RENDERERS_VULKAN_LIB_PHYSICAL_DEVICE_PROPERTIES_H \ No newline at end of file diff --git a/include/fennec/renderers/vulkan/lib/surface.h b/include/fennec/renderers/vulkan/lib/surface.h new file mode 100644 index 0000000..2686303 --- /dev/null +++ b/include/fennec/renderers/vulkan/lib/surface.h @@ -0,0 +1,59 @@ +// ===================================================================================================================== +// fennec, a free and open source game engine +// Copyright © 2025 Medusa Slockbower +// +// This program is free software: you can redistribute it and/or modify +// it under the terms of the GNU General Public License as published by +// the Free Software Foundation, either version 3 of the License, or +// (at your option) any later version. +// +// This program is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. +// +// You should have received a copy of the GNU General Public License +// along with this program. If not, see . +// ===================================================================================================================== + +/// +/// \file surface.h +/// \brief +/// +/// +/// \details +/// \author Medusa Slockbower +/// +/// \copyright Copyright © 2025 - 2026 Medusa Slockbower ([GPLv3](https://www.gnu.org/licenses/gpl-3.0.en.html)) +/// +/// + + +#ifndef FENNEC_RENDERERS_VULKAN_LIB_SURFACE_H +#define FENNEC_RENDERERS_VULKAN_LIB_SURFACE_H +#include + +namespace fennec::vk +{ + +class surface { +public: + + /// + /// \brief Surface Constructor. + /// \param surface The surface to take ownership of. + surface(VkSurfaceKHR surface) + : _handle(surface) { + } + + VkSurfaceKHR handle() const { + return _handle; + } + +private: + VkSurfaceKHR _handle; +}; + +} + +#endif // FENNEC_RENDERERS_VULKAN_LIB_SURFACE_H \ No newline at end of file diff --git a/include/fennec/renderers/vulkan/vkcontext.h b/include/fennec/renderers/vulkan/vkcontext.h index 1816b00..1f909a0 100644 --- a/include/fennec/renderers/vulkan/vkcontext.h +++ b/include/fennec/renderers/vulkan/vkcontext.h @@ -32,20 +32,88 @@ #ifndef FENNEC_PLATFORM_VULKAN_VKCONTEXT_H #define FENNEC_PLATFORM_VULKAN_VKCONTEXT_H -#include +#include #include +#include +#include namespace fennec { -class vkcontext : public gfxcontext { -public: - vkcontext(display_server* display); - ~vkcontext(); +/// +/// \brief Vulkan Context +class vkcontext : public gfxcontext, public vk::debugger { +// Constructor & Destructor ============================================================================================ +public: + + /// \name Constructor & Destructor + /// @{ + + /// + /// \brief Context Constructor + /// \param display The display server + /// \param extensions The required extensions for the implementation + /// + /// \note An override ***should not*** accept \emph{extensions} as an argument and should instead provide it directly + /// to the constructor for the extensions your implementation needs. For example: + /// ```cpp + /// class wayland_vkcontext : public vkcontext { + /// wayland_vkcontext(display_server* display) + /// : vkcontext(display, { "VK_KHR_wayland_surface" }) { + /// } + /// } + /// ``` + explicit vkcontext(display_server* display, const dynarray& extensions); + + /// + /// \brief Context Destructor + ~vkcontext() override; + + /// @} + + +// Properties ========================================================================================================== +public: + + /// \name Properties + /// @{ + + /// + /// \brief Context Validity + /// \returns \emph{true} if the context is initialized and valid, \emph{false} otherwise. bool is_valid() override; + vk::instance* get_instance() { + return instance.get(); + } + + /// @} + + +// Debug Callbacks ===================================================================================================== +public: + + void message(uint32_t severity, + uint32_t type, + const cstring& id, + const cstring& message, + const dynarray& queue, + const dynarray& commands, + const dynarray& objects) override; + + static uint32_t translate_severity(uint32_t x) { + switch (x) { + default: + case vk::debug_message_severity_info: return logger::info; + case vk::debug_message_severity_verbose: return logger::alert; + case vk::debug_message_severity_warning: return logger::warning; + case vk::debug_message_severity_error: return logger::error; + } + } + protected: + unique_ptr instance; }; } // fennec diff --git a/include/fennec/renderers/opengl/lib/vertex_array.h b/include/fennec/renderers/vulkan/vksurface.h similarity index 57% rename from include/fennec/renderers/opengl/lib/vertex_array.h rename to include/fennec/renderers/vulkan/vksurface.h index d5d0228..ab069e4 100644 --- a/include/fennec/renderers/opengl/lib/vertex_array.h +++ b/include/fennec/renderers/vulkan/vksurface.h @@ -1,6 +1,6 @@ // ===================================================================================================================== // fennec, a free and open source game engine -// Copyright © 2025 - 2026 Medusa Slockbower +// Copyright © 2025 Medusa Slockbower // // This program is free software: you can redistribute it and/or modify // it under the terms of the GNU General Public License as published by @@ -17,7 +17,7 @@ // ===================================================================================================================== /// -/// \file fennec/renderers/opengl/lib/vertex_array.h +/// \file vksurface.h /// \brief /// /// @@ -28,48 +28,36 @@ /// /// -#ifndef FENNEC_RENDERERS_OPENGL_LIB_VERTEX_ARRAY_H -#define FENNEC_RENDERERS_OPENGL_LIB_VERTEX_ARRAY_H -#include -#include +#ifndef FENNEC_RENDERERS_VULKAN_VKSURFACE_H +#define FENNEC_RENDERERS_VULKAN_VKSURFACE_H + +#include +#include namespace fennec { -namespace gl -{ +class vksurface : public gfxsurface { +private: + + using surface_t = unique_ptr; -class vertex_array { public: - constexpr vertex_array() - : _handle(NULL) { - glGenVertexArrays(1, &_handle); - } + vksurface(fennec::window* win, gfxcontext* ctx, surface_t&& surface); - constexpr ~vertex_array() { - glDeleteVertexArrays(1, &_handle); - } + ~vksurface(); - constexpr void use() const { - glBindVertexArray(_handle); - } + void make_current() override; - constexpr void set_attribute(GLuint i, GLenum type, GLint n, GLintptr offset, GLboolean normalized = false) { - glVertexAttribFormat(i, n, type, normalized, offset); - glEnableVertexAttribArray(i); - } + void swap() override; - constexpr void clear_attribute(GLuint i) { - glDisableVertexAttribArray(i); - } + void resize(const ivec2& size) override; private: - GLuint _handle; + surface_t _surface; }; } -} - -#endif // FENNEC_RENDERERS_OPENGL_LIB_VERTEX_ARRAY_H +#endif // FENNEC_RENDERERS_VULKAN_VKSURFACE_H diff --git a/include/fennec/rtti/detail/_constants.h b/include/fennec/rtti/detail/_constants.h index 0fcddb4..5789c0f 100644 --- a/include/fennec/rtti/detail/_constants.h +++ b/include/fennec/rtti/detail/_constants.h @@ -24,8 +24,8 @@ namespace fennec::detail { -// const char* fennec::detail::f() [with T = void] -inline static constexpr size_t type_name_f_heading = 42; +// const char *fennec::detail::f() [T = void] +inline static constexpr size_t type_name_f_heading = 37; inline static constexpr size_t type_name_f_footing = 1; } diff --git a/include/fennec/rtti/enable.h b/include/fennec/rtti/enable.h index 4e2e8f9..f3c6947 100644 --- a/include/fennec/rtti/enable.h +++ b/include/fennec/rtti/enable.h @@ -38,6 +38,33 @@ #include +#if FENNEC_COMPILER_CLANG + +/// +/// \brief Enable the class of the current scope for Run-Time Type Information +/// +/// \details Any base classes that need to be reflected on should be included as parameters. +#define FENNEC_RTTI_CLASS_ENABLE(...) \ +public: \ + _Pragma("clang diagnostic push") \ + _Pragma("clang diagnostic ignored \"-Winconsistent-missing-override\"") \ + /*! \name RTTI \ + * @{ */ \ + \ + /*! \brief A list of super classes */ \ + using super_class_list = fennec::typelist<__VA_ARGS__>; \ + \ + /*! \ + * \brief Getter for the object type */ \ + virtual inline fennec::type get_type() const { return fennec::type::get_from_instance(this); } \ + FENNEC_DEFINE_THIS_T; \ + /*! @} */ \ +private: \ + FENNEC_CLASS_STATIC_CONSTRUCTOR(_init_reflection) \ + _Pragma("clang diagnostic pop") + +#else + /// /// \brief Enable the class of the current scope for Run-Time Type Information /// @@ -56,4 +83,6 @@ public: \ private: \ FENNEC_CLASS_STATIC_CONSTRUCTOR(_init_reflection) +#endif + #endif // FENNEC_RTTI_ENABLE_H \ No newline at end of file diff --git a/include/fennec/rtti/singleton.h b/include/fennec/rtti/singleton.h index 6a7ff50..f4e380d 100644 --- a/include/fennec/rtti/singleton.h +++ b/include/fennec/rtti/singleton.h @@ -36,17 +36,35 @@ namespace fennec { +/// +/// \brief Interface for defining a singleton instance +/// \tparam T The type of the singleton template struct singleton { + +// Instance Acquisition ================================================================================================ +public: + + /// \name Instance Acquisition + /// @{ + + /// + /// \brief Acquire the singleton instance. + /// \returns A reference to the instance. static T& instance() requires(is_pointer_v) { static T instance = nullptr; return instance; } + /// + /// \brief Acquire the singleton instance. + /// \returns A reference to the instance. static T& instance() requires(not is_pointer_v) { static T instance; return instance; } + + /// @} }; } diff --git a/include/fennec/rtti/this_t.h b/include/fennec/rtti/this_t.h index 035b92d..17c56d6 100644 --- a/include/fennec/rtti/this_t.h +++ b/include/fennec/rtti/this_t.h @@ -24,7 +24,7 @@ /// \details /// \author Medusa Slockbower /// -/// \copyright Copyright © 2025 Medusa Slockbower ([GPLv3](https://www.gnu.org/licenses/gpl-3.0.en.html)) +/// \copyright Copyright © 2025 - 2026 Medusa Slockbower ([GPLv3](https://www.gnu.org/licenses/gpl-3.0.en.html)) /// /// @@ -35,13 +35,13 @@ #include /// -/// \brief Deduces the type of the current class / struct scope and aliases it as \f$this\_t\f$. +/// \brief Deduces the type of the current class / struct scope and aliases it as \emph{this_t}. #define FENNEC_DEFINE_THIS_T \ private: \ struct _this_t_tag {}; \ constexpr auto _this_t_helper() -> decltype(fennec::detail::_this::writer<_this_t_tag, decltype(this)>{}, void()) {} \ public: \ -/*! \brief Definition of \f$this\_t\f$, used for RTTI */ \ +/*! \brief Definition of \emph{this_t}, used for RTTI */ \ using this_t = fennec::detail::_this::read<_this_t_tag> #endif // FENNEC_RTTI_THIS_T_H \ No newline at end of file diff --git a/include/fennec/rtti/type.h b/include/fennec/rtti/type.h index 4a1eff1..5890c98 100644 --- a/include/fennec/rtti/type.h +++ b/include/fennec/rtti/type.h @@ -37,8 +37,77 @@ namespace fennec { +/// +/// \brief A struct representing traits of a type, deduced at run-time. struct type { +// Constructors & Destructor =========================================================================================== +public: + + /// \name Constructors & Destructor + /// @{ + + /// + /// \brief Default Constructor + /// \details Initializes with null backing data. + type() + : type(nullptr) { + } + + /// + /// \brief Data Constructor + /// \param d Type data to reference + /// + /// \note This function is only meant to be used internally. + /// If you're using it, you're probably doing something wrong. + type(type_data* d) + : _data(d) { + } + + /// + /// \brief Copy Constructor + /// \param t Type to copy + type(const type& t) = default; + + /// + /// \brief Move Constructor + /// \param t Type to move. + type(type&& t) noexcept = default; + + /// + /// \brief Trivial Destructor + ~type() = default; + + /// @} + + +// Assignment ========================================================================================================== +public: + + /// \name Assignment + /// @{ + + /// + /// \brief Copy Assignment + /// \param t Type to copy + /// \returns A reference to \emph{this} after copying \emph{t} + type& operator=(const type& t) = default; + + /// + /// \brief Move Assignment + /// \param t Type to move + /// \returns A reference to \emph{this} after copying \emph{t} + type& operator=(type&& t) noexcept = default; + + /// @} + + +// Properties ========================================================================================================== +public: + + /// \name Properties + /// @{ + /// /// \returns A const-qualified reference to a string containing the name of the type const string& name() const { @@ -65,25 +134,25 @@ struct type { } /// - /// \returns \f$true\f$ if this is a complete type, false otherwise + /// \returns \emph{true} if this is a complete type, false otherwise bool is_complete() const { return _data ? _data->properties.test(type_data::property_complete) : false; } /// - /// \returns \f$true\f$ if this type fulfills the [C++11 range-initializer](https://en.cppreference.com/w/cpp/language/range-for.html), false otherwise + /// \returns \emph{true} if this type fulfills the [C++11 range-initializer](https://en.cppreference.com/w/cpp/language/range-for.html), false otherwise bool is_iterable() const { return _data ? _data->properties.test(type_data::property_iterable) : false; } /// - /// \returns \f$true\f$ if this type implements `operator[]` with a single parameter of integral type, false otherwise + /// \returns \emph{true} if this type implements `operator[]` with a single parameter of integral type, false otherwise bool is_indexable() const { return _data ? _data->properties.test(type_data::property_indexable) : false; } /// - /// \returns \f$true\f$ if this type implements `operator[]` with a single parameter of type `type::key_t` + /// \returns \emph{true} if this type implements `operator[]` with a single parameter of type `type::key_t` bool is_mappable() const { return _data ? _data->properties.test(type_data::property_mappable) : false; } @@ -94,6 +163,15 @@ struct type { return _data ? _data->key_type : nullptr; } + /// @} + + +// Comparison ========================================================================================================== +public: + + /// \name Comparison + /// @{ + /// /// \brief Type Equality Operator /// \param c The type to check against @@ -102,12 +180,31 @@ struct type { return _data == c._data; } + /// + /// \brief Type Inequality Operator + /// \param c The type to check against + /// \returns True if the types are identical, false otherwise. + bool operator!=(const type& c) const { + return _data != c._data; + } + + /// @} + + +// Type Retrieval ====================================================================================================== +public: + + /// \name Type Retrieval + /// @{ + /// /// \brief Get the type info of the specified type /// \tparam TypeT The type to check /// \returns A type struct containing information about TypeT template - static type get() { return type(static_cast(nullptr)); } + static type get() { + return type(static_cast(nullptr)); + } /// /// \brief Get the type info of the provided object. @@ -115,7 +212,9 @@ struct type { /// \param t A pointer to an object /// \returns The type info of the provided type template - static type get_from_instance(TypeT* t) { return type(t); } + static type get_from_instance(TypeT* t) { + return type(t); + } /// /// \brief Get the type info of the provided object. @@ -123,23 +222,25 @@ struct type { /// \param t A pointer to an object /// \returns The type info of the provided type template - static type get_from_instance(const TypeT*) { return type(static_cast(nullptr)); } + static type get_from_instance(const TypeT*) { + return type(static_cast(nullptr)); + } + /// @} + + +// Private Member Variables ============================================================================================ private: const type_data* _data; + +// Private Helpers ===================================================================================================== +private: template type(TypeT*) : _data(type_storage::get_data()) { } -public: - type(type_data* d) : _data(d) { } - type(const type& t) = default; - type(type&& t) noexcept = default; - - type& operator=(const type&) = default; - type& operator=(type&&) noexcept = default; }; diff --git a/include/fennec/rtti/type_data.h b/include/fennec/rtti/type_data.h index 7cda420..59ef655 100644 --- a/include/fennec/rtti/type_data.h +++ b/include/fennec/rtti/type_data.h @@ -42,35 +42,54 @@ namespace fennec { -struct type_data { - enum property_ { - property_complete = 0, - property_iterable, - property_indexable, - property_mappable, +// Type Data =========================================================================================================== - property_count +/// +/// \brief Structure holding information about a type +struct type_data { + + /// + /// \brief Enum representing flags in a bitset for the presence of type traits + enum property_ { + property_complete = 0, //!< Is the type complete + property_iterable, //!< Is the type iterable, i.e. implements \emph{begin()} and \emph{end()} + property_indexable, //!< Is the type indexable, i.e. implements `operator[]` + property_mappable, //!< Is the type mappable, i.e. implements `operator[]` and defines \emph{key_t} + + property_count //!< The number of property flags }; - using properties_t = bitfield; + using properties_t = bitfield; //!< Bitfield representing the presence of type properties - uint64_t uuid; - string name; + uint64_t uuid; //!< The Unique Universal Identifier for the type + string name; //!< A string representation of the type name - type_data* raw_type; - dynarray supers; - dynarray subs; + type_data* raw_type; //!< Raw type, i.e. \emph{remove_cvrefptr_t} + dynarray supers; //!< The super types of the class + dynarray subs; //!< The sub types of the class - properties_t properties; + properties_t properties; //!< The property flags - type_data* key_type; + type_data* key_type; //!< The key type for mappable types. }; + +// Type Storage ======================================================================================================== + +/// +/// \brief Structure holding all types acquired at runtime. struct type_storage { + +// Definitions ========================================================================================================= private: + template using _super_class_list = typename ClassT::super_class_list; template using _key_t = typename ClassT::key_t; + +// Private Helpers ===================================================================================================== +private: + static dynarray>& _typelist() { static dynarray> typelist; return typelist; @@ -101,16 +120,29 @@ private: return res; } + +// Run-Time Type Deduction ============================================================================================= public: + + /// \name Run-Time Type Deduction + /// @{ + + /// + /// \tparam T Type to deduce + /// \returns A pointer to the data for \emph{T}. template static type_data* get_data() { return nullptr; } + /// + /// \brief Deduce information for the provided type + /// \tparam T Type to deduce + /// \returns A pointer to the data for \emph{T}. template static type_data* get_data() requires(not is_void_v) { - auto& typelist = _typelist(); - uint64_t uuid = typeuuid(); + auto& typelist = _typelist(); + const uint64_t uuid = typeuuid(); if (typelist.size() <= uuid) { typelist.resize(uuid * 2); @@ -123,12 +155,18 @@ public: return typelist[uuid].get(); } + /// + /// \brief Deduce information for a list of types. + /// \tparam Ts Types to deduce + /// \returns An array of pointers to the data for \emph{Ts...} template static dynarray get_data(typelist) { return { get_data()... }; } + + /// @} }; } diff --git a/include/fennec/rtti/type_registry.h b/include/fennec/rtti/type_registry.h index c9d9b6b..eaa7599 100644 --- a/include/fennec/rtti/type_registry.h +++ b/include/fennec/rtti/type_registry.h @@ -40,59 +40,130 @@ namespace fennec { +/// +/// \brief Interface for defining a registry of types. +/// \tparam BaseT The base type of the registry +/// \tparam ArgsT Arguments for constructing the type template class type_registry { + +// Definitions ========================================================================================================= public: - using ctor_t = BaseT* (*)(ArgsT...); + /// \name Definitions + /// @{ + + using ctor_t = BaseT* (*)(ArgsT...); //!< Signature for a function that calls the constructor. + + /// + /// \brief Struct holding a type entry. struct entry { - size_t priority; - type type; - ctor_t ctor; + // Public Member Variables ----------------------------------------------------------------------------------------- + public: + size_t priority; //!< A priority value associated with the type + type type; //!< Type information for the entry + ctor_t ctor; //!< A constructor for the type + + + // Constructors & Destructor --------------------------------------------------------------------------------------- + public: + + /// \name Constructors & Destructor + /// @{ + + /// + /// \brief Default Constructor + /// + /// \details Holds a priority of \math{0}, null type, and null constructor. entry() : priority(0) - , type(nullptr) + , type() , ctor(nullptr) { } + /// + /// \brief Copy Constructor + /// \param e The entry to copy entry(const entry& e) : priority(e.priority) , type(e.type) , ctor(e.ctor) { } + /// + /// \brief Copy Constructor + /// \param e The entry to move entry(entry&& e) noexcept : priority(e.priority) , type(e.type) , ctor(e.ctor) { } - ~entry() { - } - - entry& operator=(const entry& e) { - priority = e.priority; - type = e.type; - ctor = e.ctor; - return *this; - } - - entry& operator=(entry&&) noexcept = default; - + /// + /// \brief Entry Constructor + /// \param p The priority of the entry + /// \param type The type info + /// \param ctor A function that constructs the type entry(size_t p, fennec::type type, ctor_t ctor) : priority(p), type(type), ctor(ctor) { } + + /// + /// \brief Destructor + ~entry() = default; + + /// @} + + + // Assignment ------------------------------------------------------------------------------------------------------ + public: + + /// \name Assignment + /// @{ + + /// + /// \brief Copy Assignment + /// \param e The entry to copy + /// \returns A reference to \emph{this} after copying \emph{e}. + entry& operator=(const entry& e) = default; + + /// + /// \brief Move Assignment + /// \param e The entry to move + /// \returns A reference of self after moving \emph{e}. + entry& operator=(entry&& e) noexcept = default; + + /// @} }; + /// + /// \brief Comparison for entries struct compare { bool operator()(const entry& a, const entry& b) const { +#if FENNEC_COMPILER_CLANG +#pragma clang diagnostic push +#pragma clang diagnostic ignored "-Wordered-compare-function-pointers" +#endif return a.priority > b.priority and a.ctor < b.ctor; +#if FENNEC_COMPILER_CLANG +#pragma clang diagnostic pop +#endif } }; - using entrylist_t = priority_queue; + using entrylist_t = priority_queue; //!< A list of type entries. + +// Type Registration =================================================================================================== + + /// \name Type Registration + /// @{ + + /// + /// \brief Type Registration Function + /// \tparam DerivedT The derived type to register + /// \param priority The priority of the type template requires(is_base_of_v) static void register_type(size_t priority = 0) { _global_list().emplace( @@ -102,10 +173,17 @@ public: ); } + /// + /// \brief Get the list of registered types + /// \returns A reference to the list of types. static const entrylist_t& get_type_list() { return _global_list(); } + /// @} + + +// Private Helpers ===================================================================================================== private: static entrylist_t& _global_list() { static entrylist_t list; diff --git a/include/fennec/rtti/typeid.h b/include/fennec/rtti/typeid.h index f401ef8..b712c10 100644 --- a/include/fennec/rtti/typeid.h +++ b/include/fennec/rtti/typeid.h @@ -25,8 +25,13 @@ namespace fennec { -constexpr uint64_t nullid = 0; +constexpr uint64_t nullid = 0; //!< Constant Representing a null typeid. +/// +/// \brief ID Generation +/// \tparam TypeT The type +/// \tparam RootT The base type +/// \returns An ID Generated for \emph{TypeT} template FENNEC_NO_INLINE uint64_t typeuuid() { static bool init = false; diff --git a/include/fennec/rtti/typelist.h b/include/fennec/rtti/typelist.h index 3ea0bcb..90bbd91 100644 --- a/include/fennec/rtti/typelist.h +++ b/include/fennec/rtti/typelist.h @@ -37,15 +37,22 @@ namespace fennec { +/// +/// \brief Type List Interface struct vtypelist { virtual ~vtypelist() = default; virtual dynarray get() = 0; }; +/// +/// \brief Static Type List template struct typelist : vtypelist { static constexpr size_t size = sizeof...(TypesT); + /// + /// \brief Get the type information for \emph{TypesT...} + /// \returns An array of the types virtual dynarray get() { return { type::get()... }; } diff --git a/include/fennec/scene/component.h b/include/fennec/scene/component.h index 64cd3ea..4b40bd9 100644 --- a/include/fennec/scene/component.h +++ b/include/fennec/scene/component.h @@ -33,9 +33,7 @@ public: // Public Member Variables ============================================================================================= public: - /// - /// \brief reference to the - scene_node* const node; + scene_node* const node; //!< Reference to the node that owns this component. component(scene_node* node) : node(node) { diff --git a/include/fennec/scene/node2d.h b/include/fennec/scene/node2d.h index 1ad6ae2..95b064e 100644 --- a/include/fennec/scene/node2d.h +++ b/include/fennec/scene/node2d.h @@ -48,16 +48,19 @@ struct transform_update_2d : event { node2d* node; FENNEC_RTTI_CLASS_ENABLE(event) { - } }; +/// +/// \brief 2D Scene Node struct node2d : scene_node { // Definitions ========================================================================================================= + /// + /// \brief Node Mobility enum mobility_ : bool { - mobility_static = false, - mobility_free = true + mobility_static = false, //!< Promise that this node won't have any transform changes. + mobility_free = true //!< No transform restrictions. }; @@ -142,7 +145,7 @@ public: } } - constexpr void commit() { + constexpr void apply() { if (not _mobility) { return; } diff --git a/include/fennec/scene/scene.h b/include/fennec/scene/scene.h index 42722c2..ab8380e 100644 --- a/include/fennec/scene/scene.h +++ b/include/fennec/scene/scene.h @@ -38,8 +38,8 @@ class scene { // Definitions ========================================================================================================= private: - using elem_t = unique_ptr; - using table_t = rdtree; + using elem_t = unique_ptr; + using tree_t = rdtree; // Access ============================================================================================================== @@ -48,18 +48,18 @@ public: /// \brief Find a node by name. /// \details If multiple nodes have the same name, finds the first one in pre-order traversal. /// \param name The name of the node to search for - /// \returns The id of the node, \f$npos\f$ if not found. + /// \returns The id of the node, \emph{npos} if not found. scene_node* operator[](const cstring& name) const; /// /// \brief Find a node by name. /// \details If multiple nodes have the same name, finds the first one in pre-order traversal. /// \param name The name of the node to search for - /// \returns The id of the node, \f$npos\f$ if not found. + /// \returns The id of the node, \emph{npos} if not found. scene_node* operator[](const string& name) const; private: - table_t _table; + tree_t _tree; }; } diff --git a/include/fennec/string/cstring.h b/include/fennec/string/cstring.h index 6dcde44..6b0daa1 100644 --- a/include/fennec/string/cstring.h +++ b/include/fennec/string/cstring.h @@ -48,12 +48,6 @@ using ::ispunct; using ::tolower; using ::toupper; - -struct string_view { - const char* str; - size_t len; -}; - /// /// \brief This struct wraps c-style strings /// @@ -62,11 +56,29 @@ struct string_view { /// This struct should be used when fennec::string would make unnecessary dynamic buffers. struct cstring { +// Definitions & Constants ============================================================================================= public: - static constexpr size_t npos = -1; - using char_t = char; -// Constructors ======================================================================================================== + /// \name Definitions + /// @{ + + using char_t = char; //!< The character type. + + /// @} + + + /// \name Constants + /// @{ + + static constexpr size_t npos = -1; //!< Constant representing a null position in the string. + + /// @} + +// Constructors & Destructor =========================================================================================== +public: + + /// \name Constructors & Destructor + /// @{ /// /// \brief Default Constructor, initializes with nullptr @@ -83,8 +95,6 @@ public: /// /// \param str the buffer to wrap /// \param n the number of characters in the buffer plus the null terminator - /// - /// \note If used with `::strlen`, the result should be incremented by 1 to include the null terminator constexpr cstring(char* str, size_t n) : _str(str) , _size(n) @@ -110,8 +120,6 @@ public: /// /// \param str the buffer to wrap /// \param n the number of characters in the buffer plus the null terminator - /// - /// \note If used with `::strlen`, the result should be incremented by 1 to include the null terminator constexpr cstring(const char* str, size_t n) : _cstr(str) , _size(n) @@ -147,32 +155,64 @@ public: str._const = true; } - // TODO: Document - constexpr cstring(const cstring&) = delete; + /// + /// \brief Copy Constructor + /// \param str object to copy + constexpr cstring(const cstring& str) + : _cstr(str._cstr) + , _size(str._size) + , _const(str._const) { + } + + /// + /// \brief Destructor constexpr ~cstring() = default; + /// @} + + +// Assignment ========================================================================================================== +public: + + /// \name Assignment + /// @{ + + /// + /// \brief Null Assignment + /// \returns A reference to \emph{this} after clearing the held reference. constexpr cstring& operator=(nullptr_t) { _str = nullptr, _size = 0, _const = true; return *this; } - // TODO: Document - template - constexpr cstring& operator=(char(&str)[n]) { - assert(_str[n - 1] == '\0', "Invalid NTBS."); - _str = str, _size = n - 1, _const = false; + /// + /// \tparam N + /// \param str + /// \return + template + constexpr cstring& operator=(char(&str)[N]) { + assert(_str[N - 1] == '\0', "Invalid NTBS."); + _str = str, _size = N - 1, _const = false; return *this; } - // TODO: Document - template - constexpr cstring& operator=(const char(&str)[n]) { - assert(str[n - 1] == '\0', "Invalid NTBS."); - _cstr = str; _size = n - 1; _const = true; + /// + /// \brief Array Constructor + /// \tparam N The length of the array. + /// \param str A reference to the array. + /// \returns A reference to \emph{this} after having assigned and validated \emph{str} + template + constexpr cstring& operator=(const char(&str)[N]) { + assert(str[N - 1] == '\0', "Invalid NTBS."); + _cstr = str; _size = N - 1; _const = true; return *this; } - // TODO: Document + /// + /// \brief Array Constructor + /// \tparam N The length of the array. + /// \param str A reference to the array. + /// \returns A reference to \emph{this} after having taken ownership of \emph{str} constexpr cstring& operator=(cstring&& str) noexcept { _cstr = str._cstr; str._cstr = nullptr; _size = str._size; str._size = 0; @@ -180,8 +220,25 @@ public: return *this; } + /// + /// \brief Copy Assignment + /// \param str The object to copy + /// \returns A reference to \emph{this} + constexpr cstring& operator=(const cstring& str) { + _cstr = str._cstr; + _size = str._size; + _const = str._const; + return *this; + } + + /// @} + // Properties ========================================================================================================== +public: + + /// \name Properties + /// @{ /// /// \returns the size of the string excluding its null terminator, i.e. `(*str)[size()] == '\0'` @@ -195,12 +252,20 @@ public: return _size + 1; } + /// + /// \returns \emph{true} if there is no held string, or the size is \math{0}, \emph{false} otherwise. constexpr bool is_empty() const { return _cstr == nullptr || _size == 0; } + /// @} + // Access ============================================================================================================== +public: + + /// \name Access + /// @{ /// /// \brief Array Access Operator @@ -241,9 +306,14 @@ public: return _cstr; } + /// @} + // Examination ========================================================================================================= + /// \name Examination + /// @{ + /// /// \returns The length of the string to the first null-terminator constexpr size_t length() const { @@ -269,7 +339,7 @@ public: /// /// \brief String Equality /// \param str the string to compare against - /// \returns \f$true\f$ if all characters are equal, \f$false\f$ otherwise + /// \returns \emph{true} if all characters are equal, \emph{false} otherwise template constexpr bool operator==(const char (&str)[n]) const { return compare(cstring(str)) == 0; @@ -278,23 +348,23 @@ public: /// /// \brief String Equality /// \param str the string to compare against - /// \returns \f$true\f$ if all characters are equal, \f$false\f$ otherwise + /// \returns \emph{true} if all characters are equal, \emph{false} otherwise constexpr bool operator==(const cstring& str) const { return compare(str) == 0; } /// /// \brief nullptr Equality - /// \returns \f$true\f$ if there is no held string, \f$false\f$ otherwise. + /// \returns \emph{true} if there is no held string, \emph{false} otherwise. constexpr bool operator==(nullptr_t) const { return _cstr == nullptr; } /// - /// \brief Finds the index of the first occurrence of \f$c\f$ in the string + /// \brief Finds the index of the first occurrence of \emph{c} in the string /// \param c the character to find /// \param i the index to start at - /// \returns The index of \f$c\f$ if it occurs in the string, otherwise returns `size()` + /// \returns The index of \emph{c} if it occurs in the string, otherwise returns `size()` constexpr size_t find(char c, size_t i = 0) const { if (i >= _size) { // bounds check return _size; @@ -305,10 +375,10 @@ public: } /// - /// \brief Finds the index of the first occurrence of \f$str\f$ in the string. + /// \brief Finds the index of the first occurrence of \emph{str} in the string. /// \param str the string to find /// \param i the index to start at - /// \returns The index of \f$str\f$ if it occurs in the string, otherwise returns `size()` + /// \returns The index of \emph{str} if it occurs in the string, otherwise returns `size()` constexpr size_t find(const cstring& str, size_t i = 0) const { if (i + str._size > _size) { // bounds check return _size; @@ -319,10 +389,10 @@ public: } /// - /// \brief Finds the index of the last occurrence of \f$c\f$ in the string. + /// \brief Finds the index of the last occurrence of \emph{c} in the string. /// \param c the string to find /// \param i the index to start at - /// \returns The index of \f$c\f$ if it occurs in the string, otherwise returns `size()` + /// \returns The index of \emph{c} if it occurs in the string, otherwise returns `size()` constexpr size_t rfind(char c, size_t i = npos) const { if (_size == 0) { return _size; @@ -336,10 +406,10 @@ public: } /// - /// \brief Finds the index of the last occurrence of \f$str\f$ in the string. + /// \brief Finds the index of the last occurrence of \emph{str} in the string. /// \param str the string to find /// \param i the index to start at - /// \returns The index of \f$str\f$ if it occurs in the string, otherwise returns `size()` + /// \returns The index of \emph{str} if it occurs in the string, otherwise returns `size()` constexpr size_t rfind(const cstring& str, size_t i = npos) const { if (_size == 0) { return _size; @@ -357,6 +427,10 @@ public: return _size; // base case } + /// @} + + +// Private Member Variables ============================================================================================ private: union { // hack to allow both const qualified and non-const strings char* _str; @@ -366,6 +440,7 @@ private: bool _const; }; +/// \brief Hashing for `fennec::cstring` template<> struct hash : hash { constexpr size_t operator()(const cstring& str) const { diff --git a/include/fennec/string/string.h b/include/fennec/string/string.h index 3e96999..ff8f803 100644 --- a/include/fennec/string/string.h +++ b/include/fennec/string/string.h @@ -20,6 +20,7 @@ #define FENNEC_STRING_STRING_H #include +#include #include #include @@ -45,14 +46,27 @@ struct _string // Definitions ========================================================================================================= public: + /// \name Constants + /// @{ + + static constexpr size_t npos = -1; //!< Constant representing a null position in the string. + + /// @} - static constexpr size_t npos = -1; //!< null position + /// \name Definitions + /// @{ + using char_t = char; //!< the character type using alloc_t = allocation; //!< the allocator type + /// @} -// Constructors ======================================================================================================== + +// Constructors & Destructor =========================================================================================== + + /// \name Constructors & Destructor + /// @{ /// /// \brief Default Constructor, initializes empty string @@ -61,7 +75,7 @@ public: } /// - /// \brief Sized Constructor, initializes a null-terminated string of size \f$n\f$ with `'c'...` + /// \brief Sized Constructor, initializes a null-terminated string of size \emph{n} with `'c'...` /// \param n the number of characters /// \param c the character to fill with /// @@ -79,7 +93,7 @@ public: } /// - /// \brief Sized Alloc Constructor, initializes a null-terminated string of size \f$n\f$ with `'c'...` + /// \brief Sized Alloc Constructor, initializes a null-terminated string of size \emph{n} with `'c'...` /// \param n the number of characters /// \param c the character to fill with /// \param alloc The allocator to use @@ -97,22 +111,6 @@ public: : _str(cstr, cstr.size() + 1) { } - /// - /// \brief Buffer Constructor, wraps the provided C-Style string, appending a null-terminator if not present - /// \param str the buffer to wrap - /// \tparam n the number of characters in the buffer including the null-terminator, if present - /// - /// \details This constructor is explicit because we want to be explicit about when we are allocating memory for - /// a string. - template - explicit constexpr _string(const char (&str)[n]) - : _str(str[n - 1] != '\0' ? n + 1 : n) { - fennec::memcpy(_str, str, n); - if (str[n - 1] != '\0') { - _str[n] = '\0'; - } - } - /// /// \brief Buffer Constructor, wraps the provided C-Style string, appending a null-terminator if not present /// \param buf the buffer to wrap @@ -146,12 +144,19 @@ public: /// \brief Destructor, cleans up underlying allocation constexpr ~_string() = default; + /// @} + + // Assignment ========================================================================================================== +public: + + /// \name Assignment + /// @{ /// /// \brief C-String Assignment /// \param cstr The C-Style string to assign. - /// \returns A reference to self + /// \returns A reference to \emph{this} constexpr _string& operator=(const cstring& cstr) { _str.allocate(cstr.capacity()); fennec::memcpy(_str, cstr, cstr.capacity()); @@ -161,7 +166,7 @@ public: /// /// \brief String Copy Assignment /// \param str the string to copy - /// \returns A reference to self + /// \returns A reference to \emph{this} constexpr _string& operator=(const _string& str) { _str = str._str; return *this; @@ -170,13 +175,20 @@ public: /// /// \brief String Move Assignment /// \param str the string to take ownership of - /// \returns A reference to self + /// \returns A reference to \emph{this} constexpr _string& operator=(_string&& str) noexcept { _str = fennec::move(str._str); return *this; } + /// @} + + // Properties ========================================================================================================== +public: + + /// \name Properties + /// @{ /// /// \returns The size of the string excluding null terminator @@ -191,12 +203,19 @@ public: } /// - /// \returns \f$true\f$ if the string contains no characters, \f$false\f$ otherwise. + /// \returns \emph{true} if the string contains no characters, \emph{false} otherwise. constexpr bool is_empty() const { return size() == 0; } + /// @} + + // Access ============================================================================================================== +public: + + /// \name Access + /// @{ /// /// \brief Array Access Operator @@ -232,7 +251,14 @@ public: return _str; } + /// @} + + // Examination ========================================================================================================= +public: + + /// \name Examination + /// @{ /// /// \returns The length of the string to the first null-terminator @@ -242,7 +268,7 @@ public: /// /// \param str the string to compare against - /// \param i An offset to start with in \f$this\f$ + /// \param i An offset to start with in \emph{this} /// \param n The number of characters to compare /// \returns Zero if both strings are equal, otherwise a negative value if lhs appears before rhs according to the /// current locale, otherwise a positive value. @@ -258,7 +284,7 @@ public: /// /// \brief String Comparison /// \param str the string to compare against - /// \param i An offset to start at in \f$this\f$ + /// \param i An offset to start at in \emph{this} /// \param n The number of characters to compare /// \returns Zero if both strings are equal, otherwise a negative value if lhs appears before rhs according to the /// current locale, otherwise a positive value. @@ -289,17 +315,17 @@ public: /// /// \brief Check if the string contains a character /// \param c The character to find - /// \param i An offset to start at in \f$this\f$ - /// \returns \f$true\f$ if \f$c\f$ is contained in \f$this\f$ + /// \param i An offset to start at in \emph{this} + /// \returns \emph{true} if \emph{c} is contained in \emph{this} constexpr bool contains(char c, size_t i = 0) const { return find(c, i) != size(); } /// - /// \brief Finds the index of the first occurrence of \f$c\f$ in the string + /// \brief Finds the index of the first occurrence of \emph{c} in the string /// \param c the character to find - /// \param i An offset to start at in \f$this\f$ - /// \returns The index of \f$c\f$ if it occurs in the string, otherwise returns `size()` + /// \param i An offset to start at in \emph{this} + /// \returns The index of \emph{c} if it occurs in the string, otherwise returns `size()` constexpr size_t find(char c, size_t i = 0) const { if (i >= size()) { // bounds check return size(); @@ -310,10 +336,10 @@ public: } /// - /// \brief Finds the index of the first occurrence of \f$str\f$ in the string. + /// \brief Finds the index of the first occurrence of \emph{str} in the string. /// \param str the string to find - /// \param i An offset to start at in \f$this\f$ - /// \returns The index of \f$str\f$ if it occurs in the string, otherwise returns `size()` + /// \param i An offset to start at in \emph{this} + /// \returns The index of \emph{str} if it occurs in the string, otherwise returns `size()` constexpr size_t find(const string& str, size_t i = 0) const { // bounds check if (i >= size()) { // bounds check return size(); @@ -324,10 +350,10 @@ public: } /// - /// \brief Finds the index of the first occurrence of \f$str\f$ in the string. + /// \brief Finds the index of the first occurrence of \emph{str} in the string. /// \param str the string to find - /// \param i An offset to start at in \f$this\f$ - /// \returns The index of \f$str\f$ if it occurs in the string, otherwise returns `size()` + /// \param i An offset to start at in \emph{this} + /// \returns The index of \emph{str} if it occurs in the string, otherwise returns `size()` constexpr size_t find(const cstring& str, size_t i = 0) const { if (i + str.size() > size()) { // bounds check return size(); @@ -338,10 +364,10 @@ public: } /// - /// \brief Finds the index of the last occurrence of \f$c\f$ in the string. + /// \brief Finds the index of the last occurrence of \emph{c} in the string. /// \param c the string to find - /// \param i An offset to start at in \f$this\f$ - /// \returns The index of \f$c\f$ if it occurs in the string, otherwise returns `size()` + /// \param i An offset to start at in \emph{this} + /// \returns The index of \emph{c} if it occurs in the string, otherwise returns `size()` constexpr size_t rfind(char c, size_t i = npos) const { if (size() == 0) { return size(); @@ -356,10 +382,10 @@ public: } /// - /// \brief Finds the index of the last occurrence of \f$str\f$ in the string. + /// \brief Finds the index of the last occurrence of \emph{str} in the string. /// \param str the string to find - /// \param i An offset to start at in \f$this\f$ - /// \returns The index of \f$str\f$ if it occurs in the string, otherwise returns `size()` + /// \param i An offset to start at in \emph{this} + /// \returns The index of \emph{str} if it occurs in the string, otherwise returns `size()` constexpr size_t rfind(const cstring& str, size_t i = npos) const { if (size() == 0) { return size(); @@ -377,10 +403,10 @@ public: } /// - /// \brief Finds the index of the last occurrence of \f$str\f$ in the string. + /// \brief Finds the index of the last occurrence of \emph{str} in the string. /// \param str the string to find - /// \param i An offset to start at in \f$this\f$ - /// \returns The index of \f$str\f$ if it occurs in the string, otherwise returns `size()` + /// \param i An offset to start at in \emph{this} + /// \returns The index of \emph{str} if it occurs in the string, otherwise returns `size()` constexpr size_t rfind(const string& str, size_t i = npos) const { if (size() == 0) { return size(); @@ -399,9 +425,9 @@ public: /// /// \brief Retrieve a substring of a string - /// \param i An offset to start at in \f$this\f$ + /// \param i An offset to start at in \emph{this} /// \param n the number of characters - /// \returns A new string containing the range of characters specified by \f$i\f$ and \f$n\f$ + /// \returns A new string containing the range of characters specified by \emph{i} and \emph{n} constexpr _string substring(size_t i, size_t n = npos) const { if (i >= size() || n == 0) { return _string(""); @@ -413,13 +439,18 @@ public: return res; } + /// @} // Modifiers =========================================================================================================== +public: + + /// \name Modifiers + /// @{ /// /// \brief String Resize - /// \brief Resizes the underlying allocation to hold \f$n\f$ characters and a null terminator. + /// \brief Resizes the underlying allocation to hold \emph{n} characters and a null terminator. /// \param n The new size of the string constexpr void resize(size_t n) { _str.reallocate(n + 1); @@ -429,7 +460,7 @@ public: /// /// \brief Character Append /// \param c A character to append - /// \returns A new string containing the previous contents and an additional character \f$c\f$. + /// \returns A new string containing the previous contents and an additional character \emph{c}. constexpr _string operator+(char c) const { if (_str == nullptr) { return _string(1, c); @@ -444,7 +475,7 @@ public: /// /// \brief Character Prepend /// \param c A character to append - /// \returns A new string containing the character \f$c\f$ followed by the previous contents. + /// \returns A new string containing the character \emph{c} followed by the previous contents. friend constexpr _string operator+(char c, const _string& str) { _string res(str.size() + 1); res[0] = c; @@ -454,7 +485,7 @@ public: /// /// \param cstr The string to append - /// \returns A new string containing the previous contents followed by the contents of \f$cstr\f$ + /// \returns A new string containing the previous contents followed by the contents of \emph{cstr} constexpr _string operator+(const cstring& cstr) const { if (_str == nullptr) { return _string(cstr); @@ -469,7 +500,7 @@ public: /// /// \brief String Append /// \param str The string to append - /// \returns A new string containing the previous contents followed by the contents of \f$cstr\f$ + /// \returns A new string containing the previous contents followed by the contents of \emph{cstr} constexpr _string operator+(const _string& str) const { if (_str == nullptr) { return _string(str); @@ -487,10 +518,10 @@ public: /// /// \brief Character Append Assignment /// \param c A character to append - /// \returns \f$this\f$ string containing an additional character \f$c\f$. + /// \returns \emph{this} string containing an additional character \emph{c}. constexpr _string& operator+=(char c) { if (_str == nullptr) { - _str.allocate(2); + _str.allocate(2); // TODO: Performance Improvements with Capacity Expansion _str[0] = c; return *this; } @@ -501,7 +532,7 @@ public: /// /// \param cstr The string to append - /// \returns \f$this\f$ string expanded to additionally contain \f$cstr\f$ + /// \returns \emph{this} string expanded to additionally contain \emph{cstr} constexpr _string& operator+=(const cstring& cstr) { if (_str == nullptr) { return *this = cstr; @@ -515,7 +546,7 @@ public: /// /// \brief String Append Assignment /// \param str The string to append - /// \returns \f$this\f$ string expanded to additionally contain \f$str\f$ + /// \returns \emph{this} string expanded to additionally contain \emph{str} constexpr _string& operator+=(const _string& str) { if (_str == nullptr) { return *this = str; @@ -529,8 +560,14 @@ public: return *this; } + /// @} + // Iteration =========================================================================================================== +public: + + /// \name Iteration + /// @{ /// /// \returns A pointer to the first character in the string. @@ -559,14 +596,18 @@ public: return _str.data() + _str.capacity(); } + /// @} + +// Private Member Variables ============================================================================================ private: alloc_t _str; }; -template<> -struct hash : hash { - constexpr size_t operator()(const string& str) const { +/// \brief Hashing for `fennec::string` +template +struct hash<_string> : hash { + constexpr size_t operator()(const _string& str) const { return hash::operator()(byte_array(str.data(), str.size())); } }; diff --git a/include/fennec/string/string_view.h b/include/fennec/string/string_view.h new file mode 100644 index 0000000..eb3e733 --- /dev/null +++ b/include/fennec/string/string_view.h @@ -0,0 +1,57 @@ +// ===================================================================================================================== +// fennec, a free and open source game engine +// Copyright © 2025 Medusa Slockbower +// +// This program is free software: you can redistribute it and/or modify +// it under the terms of the GNU General Public License as published by +// the Free Software Foundation, either version 3 of the License, or +// (at your option) any later version. +// +// This program is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. +// +// You should have received a copy of the GNU General Public License +// along with this program. If not, see . +// ===================================================================================================================== + +/// +/// \file string_view.h +/// \brief +/// +/// +/// \details +/// \author Medusa Slockbower +/// +/// \copyright Copyright © 2025 - 2026 Medusa Slockbower ([GPLv3](https://www.gnu.org/licenses/gpl-3.0.en.html)) +/// +/// + + +#ifndef FENNEC_STRING_STRING_VIEW_H +#define FENNEC_STRING_STRING_VIEW_H + +#include + +namespace fennec +{ + +/// +/// \brief Struct representing a substring of a larger string +struct string_view { + const char* str; //!< A reference to the starting point in the string + size_t len; //!< The length of the view +}; + +/// +/// \brief Struct representing a substring of a larger string +struct wstring_view { + const wchar_t* str; //!< A reference to the starting point in the string + size_t len; //!< The length of the view +}; + + +} + +#endif // FENNEC_STRING_STRING_VIEW_H \ No newline at end of file diff --git a/include/fennec/string/wcstring.h b/include/fennec/string/wcstring.h index 65c2e91..594dca3 100644 --- a/include/fennec/string/wcstring.h +++ b/include/fennec/string/wcstring.h @@ -58,11 +58,29 @@ using ::wctrans; /// This struct should be used when fennec::string would make unnecessary dynamic buffers. struct wcstring { +// Definitions & Constants ============================================================================================= public: - static constexpr size_t npos = -1; - using char_t = wchar_t; -// Constructors ======================================================================================================== + /// \name Definitions + /// @{ + + using char_t = wchar_t; //!< The character type. + + /// @} + + + /// \name Constants + /// @{ + + static constexpr size_t npos = -1; //!< Constant representing a null position in the string. + + /// @} + +// Constructors & Destructor =========================================================================================== +public: + + /// \name Constructors & Destructor + /// @{ /// /// \brief Default Constructor, initializes with nullptr @@ -77,37 +95,44 @@ public: } /// - /// \brief Buffer Constructor, wraps the provided C-Style string /// \param str the buffer to wrap /// \param n the number of characters in the buffer plus the null terminator + /// + /// \note If used with `::strlen`, the result should be incremented by 1 to include the null terminator constexpr wcstring(wchar_t* str, size_t n) : _str(str) - , _size(n - 1) + , _size(n) , _const(false) { - assert(_str[n - 1] == '\0', "Invalid NTBS."); + if constexpr(not is_constant_evaluated()) { + assert(_str[n] == '\0', "Invalid NTBS."); + } } /// - /// \brief Buffer Constructor, wraps the provided C-Style string /// \param str the buffer to wrap /// \tparam n the number of characters in the buffer plus the null terminator template - constexpr wcstring(wchar_t (&str)[n]) + constexpr wcstring(wchar_t(&str)[n]) : _str(str) , _size(n - 1) , _const(false) { - assert(_str[n - 1] == '\0', "Invalid NTBS."); + if constexpr(not is_constant_evaluated()) { + assert(_str[n - 1] == '\0', "Invalid NTBS."); + } } /// - /// \brief Const Buffer Constructor, wraps the provided C-Style string /// \param str the buffer to wrap /// \param n the number of characters in the buffer plus the null terminator + /// + /// \note If used with `::strlen`, the result should be incremented by 1 to include the null terminator constexpr wcstring(const wchar_t* str, size_t n) : _cstr(str) - , _size(n - 1) + , _size(n) , _const(true) { - assert(_cstr[n - 1] == '\0', "Invalid NTBS."); + if constexpr(not is_constant_evaluated()) { + assert(_str[n] == '\0', "Invalid NTBS."); + } } /// @@ -115,11 +140,13 @@ public: /// \param str the buffer to wrap /// \tparam n the number of characters in the buffer plus the null terminator template - constexpr wcstring(const wchar_t (&str)[n]) + constexpr wcstring(const wchar_t(&str)[n]) : _cstr(str) , _size(n - 1) , _const(true) { - assert(_cstr[n - 1] == '\0', "Invalid NTBS."); + if constexpr(not is_constant_evaluated()) { + assert(_str[n - 1] == '\0', "Invalid NTBS."); + } } /// @@ -134,32 +161,64 @@ public: str._const = true; } - // TODO: Document - constexpr wcstring(const wcstring&) = delete; + /// + /// \brief Copy Constructor + /// \param str object to copy + constexpr wcstring(const wcstring& str) + : _cstr(str._cstr) + , _size(str._size) + , _const(str._const) { + } + + /// + /// \brief Destructor constexpr ~wcstring() = default; + /// @} + + +// Assignment ========================================================================================================== +public: + + /// \name Assignment + /// @{ + + /// + /// \brief Null Assignment + /// \returns A reference to \emph{this} after clearing the held reference. constexpr wcstring& operator=(nullptr_t) { _str = nullptr, _size = 0, _const = true; return *this; } - // TODO: Document - template - constexpr wcstring& operator=(wchar_t(&str)[n]) { - assert(_str[n - 1] == '\0', "Invalid NTBS."); - _str = str, _size = n - 1, _const = false; + /// + /// \tparam N + /// \param str + /// \return + template + constexpr wcstring& operator=(wchar_t(&str)[N]) { + assert(_str[N - 1] == '\0', "Invalid NTBS."); + _str = str, _size = N - 1, _const = false; return *this; } - // TODO: Document - template - constexpr wcstring& operator=(const wchar_t(&str)[n]) { - assert(str[n - 1] == '\0', "Invalid NTBS."); - _cstr = str; _size = n - 1; _const = true; + /// + /// \brief Array Constructor + /// \tparam N The length of the array. + /// \param str A reference to the array. + /// \returns A reference to \emph{this} after having assigned and validated \emph{str} + template + constexpr wcstring& operator=(const wchar_t(&str)[N]) { + assert(str[N - 1] == '\0', "Invalid NTBS."); + _cstr = str; _size = N - 1; _const = true; return *this; } - // TODO: Document + /// + /// \brief Array Constructor + /// \tparam N The length of the array. + /// \param str A reference to the array. + /// \returns A reference to \emph{this} after having taken ownership of \emph{str} constexpr wcstring& operator=(wcstring&& str) noexcept { _cstr = str._cstr; str._cstr = nullptr; _size = str._size; str._size = 0; @@ -167,23 +226,50 @@ public: return *this; } + /// + /// \brief Copy Assignment + /// \param str The object to copy + /// \returns A reference to \emph{this} + constexpr wcstring& operator=(const wcstring& str) { + _cstr = str._cstr; + _size = str._size; + _const = str._const; + return *this; + } + + /// @} + // Properties ========================================================================================================== +public: + + /// \name Properties + /// @{ /// /// \returns the size of the string excluding its null terminator, i.e. `(*str)[size()] == '\0'` - constexpr size_t size() const { return _size; } + constexpr size_t size() const { + return _size; + } /// /// \returns the size of the string including its null terminator, i.e. `(*str)[capacity() - 1] == '\0'` - constexpr size_t capacity() const { return _size + 1; } + constexpr size_t capacity() const { + return _size + 1; + } constexpr bool is_empty() const { return _cstr == nullptr || _size == 0; } + /// @} + // Access ============================================================================================================== +public: + + /// \name Access + /// @{ /// /// \brief Array Access Operator @@ -199,7 +285,7 @@ public: /// \brief Const-Array Access Operator /// \param i the index to access /// \returns a copy of the character - constexpr const wchar_t& operator[](size_t i) const { + constexpr wchar_t operator[](size_t i) const { assertd(i < size(), "Array Out of Bounds"); return _cstr[i]; } @@ -224,9 +310,14 @@ public: return _cstr; } + /// @} + // Examination ========================================================================================================= + /// \name Examination + /// @{ + /// /// \returns The length of the string to the first null-terminator constexpr size_t length() const { @@ -252,7 +343,7 @@ public: /// /// \brief String Equality /// \param str the string to compare against - /// \returns True if all characters are equal, false otherwise + /// \returns \emph{true} if all characters are equal, \emph{false} otherwise template constexpr bool operator==(const wchar_t (&str)[n]) const { return compare(wcstring(str)) == 0; @@ -261,23 +352,23 @@ public: /// /// \brief String Equality /// \param str the string to compare against - /// \returns True if all characters are equal, false otherwise + /// \returns \emph{true} if all characters are equal, \emph{false} otherwise constexpr bool operator==(const wcstring& str) const { return compare(str) == 0; } /// /// \brief nullptr Equality - /// \returns \f$true\f$ if there is no held string, \f$false\f$ otherwise. + /// \returns \emph{true} if there is no held string, \emph{false} otherwise. constexpr bool operator==(nullptr_t) const { return _cstr == nullptr; } /// - /// \brief Finds the index of the first occurrence of \f$c\f$ in the string + /// \brief Finds the index of the first occurrence of \emph{c} in the string /// \param c the character to find /// \param i the index to start at - /// \returns The index of \f$c\f$ if it occurs in the string, otherwise returns `size()` + /// \returns The index of \emph{c} if it occurs in the string, otherwise returns `size()` constexpr size_t find(wchar_t c, size_t i = 0) const { if (i >= _size) { // bounds check return _size; @@ -288,10 +379,10 @@ public: } /// - /// \brief Finds the index of the first occurrence of \f$str\f$ in the string. + /// \brief Finds the index of the first occurrence of \emph{str} in the string. /// \param str the string to find /// \param i the index to start at - /// \returns The index of \f$str\f$ if it occurs in the string, otherwise returns `size()` + /// \returns The index of \emph{str} if it occurs in the string, otherwise returns `size()` constexpr size_t find(const wcstring& str, size_t i = 0) const { if (i + str._size > _size) { // bounds check return _size; @@ -302,11 +393,11 @@ public: } /// - /// \brief Finds the index of the last occurrence of \f$c\f$ in the string. + /// \brief Finds the index of the last occurrence of \emph{c} in the string. /// \param c the string to find /// \param i the index to start at - /// \returns The index of \f$c\f$ if it occurs in the string, otherwise returns `size()` - constexpr size_t rfind(char c, size_t i = npos) const { + /// \returns The index of \emph{c} if it occurs in the string, otherwise returns `size()` + constexpr size_t rfind(wchar_t c, size_t i = npos) const { if (_size == 0) { return _size; } @@ -319,16 +410,16 @@ public: } /// - /// \brief Finds the index of the last occurrence of \f$str\f$ in the string. + /// \brief Finds the index of the last occurrence of \emph{str} in the string. /// \param str the string to find /// \param i the index to start at - /// \returns The index of \f$str\f$ if it occurs in the string, otherwise returns `size()` + /// \returns The index of \emph{str} if it occurs in the string, otherwise returns `size()` constexpr size_t rfind(const wcstring& str, size_t i = npos) const { if (_size == 0) { return _size; } - const char first = str[0]; + const wchar_t first = str[0]; i = min(i, _size - str._size); do { if(_cstr[i] == first) { @@ -340,6 +431,10 @@ public: return _size; // base case } + /// @} + + +// Private Member Variables ============================================================================================ private: union { // hack to allow both const qualified and non-const strings wchar_t* _str; @@ -349,6 +444,7 @@ private: bool _const; }; +/// \brief Hashing for `fennec::wcstring` template<> struct hash : hash { constexpr size_t operator()(const wcstring& str) const { diff --git a/include/fennec/string/wstring.h b/include/fennec/string/wstring.h index 5f28ca0..6055e70 100644 --- a/include/fennec/string/wstring.h +++ b/include/fennec/string/wstring.h @@ -20,9 +20,9 @@ #define FENNEC_STRING_WSTRING_H #include -#include -#include +#include +#include #include #include @@ -45,13 +45,30 @@ using wstring = _wstring<>; template struct _wstring { +// Definitions ========================================================================================================= public: - static constexpr size_t npos = -1; //!< null position + + /// \name Constants + /// @{ + + static constexpr size_t npos = -1; //!< Constant representing a null position in the string. + + /// @} + + + /// \name Definitions + /// @{ + using char_t = wchar_t; //!< the character type using alloc_t = allocation; //!< the allocator type + /// @} -// Constructors ======================================================================================================== + +// Constructors & Destructor =========================================================================================== + + /// \name Constructors & Destructor + /// @{ /// /// \brief Default Constructor, initializes empty string @@ -60,14 +77,14 @@ public: } /// - /// \brief Sized Constructor, initializes a null-terminated string of size \f$n\f$ with `'c'...` - /// \param n the number of wchar_tacters - /// \param c the wchar_tacter to fill with + /// \brief Sized Constructor, initializes a null-terminated string of size \emph{n} with `'c'...` + /// \param n the number of characters + /// \param c the character to fill with /// - /// \details adds additional wchar_tacter for null termination. + /// \details Adds additional character for null termination. constexpr _wstring(size_t n, wchar_t c = '\0') : _str(n + 1) { - fennec::wmemset(_str, c, n); + fennec::memset(_str, c, n); } /// @@ -78,15 +95,15 @@ public: } /// - /// \brief Sized Alloc Constructor, initializes a null-terminated string of size \f$n\f$ with `'c'...` + /// \brief Sized Alloc Constructor, initializes a null-terminated string of size \emph{n} with `'c'...` /// \param n the number of characters /// \param c the character to fill with /// \param alloc The allocator to use /// - /// \details adds additional character for null termination. + /// \details Adds additional character for null termination. constexpr _wstring(size_t n, wchar_t c, const alloc_t& alloc) : _str(n + 1, alloc) { - fennec::wmemset(_str, c, n); + fennec::memset(_str, c, n); } /// @@ -99,11 +116,14 @@ public: /// /// \brief Buffer Constructor, wraps the provided C-Style string, appending a null-terminator if not present /// \param str the buffer to wrap - /// \tparam n the number of wchar_tacters in the buffer including the null-terminator, if present + /// \tparam n the number of characters in the buffer including the null-terminator, if present + /// + /// \details This constructor is explicit because we want to be explicit about when we are allocating memory for + /// a string. template explicit constexpr _wstring(const wchar_t (&str)[n]) : _str(str[n - 1] != '\0' ? n + 1 : n) { - fennec::wmemcpy(_str, str, n); + fennec::memcpy(_str, str, n); if (str[n - 1] != '\0') { _str[n] = '\0'; } @@ -112,15 +132,22 @@ public: /// /// \brief Buffer Constructor, wraps the provided C-Style string, appending a null-terminator if not present /// \param buf the buffer to wrap - /// \param n the number of wchar_tacters in the buffer including the null-terminator, if present + /// \param n the number of characters in the buffer including the null-terminator, if present constexpr _wstring(const wchar_t* buf, size_t n) : _str(buf[n - 1] != '\0' ? n + 1 : n) { - fennec::wmemcpy(_str, buf, n); + fennec::memcpy(_str, buf, n); if (buf[n - 1] != '\0') { _str[n] = '\0'; } } + /// + /// \brief String View Constructor + /// \param view The C-Style string view to construct from. + constexpr _wstring(const string_view& view) + : _wstring(view.str, view.len) { + } + /// /// \brief String Copy Constructor /// \param str the string to copy @@ -135,12 +162,19 @@ public: /// \brief Destructor, cleans up underlying allocation constexpr ~_wstring() = default; + /// @} + + // Assignment ========================================================================================================== +public: + + /// \name Assignment + /// @{ /// /// \brief C-String Assignment /// \param cstr The C-Style string to assign. - /// \returns A reference to self + /// \returns A reference to \emph{this} constexpr _wstring& operator=(const wcstring& cstr) { _str.allocate(cstr.capacity()); fennec::memcpy(_str, cstr, cstr.capacity()); @@ -150,7 +184,7 @@ public: /// /// \brief String Copy Assignment /// \param str the string to copy - /// \returns A reference to self + /// \returns A reference to \emph{this} constexpr _wstring& operator=(const _wstring& str) { _str = str._str; return *this; @@ -159,13 +193,20 @@ public: /// /// \brief String Move Assignment /// \param str the string to take ownership of - /// \returns A reference to self + /// \returns A reference to \emph{this} constexpr _wstring& operator=(_wstring&& str) noexcept { _str = fennec::move(str._str); return *this; } + /// @} + + // Properties ========================================================================================================== +public: + + /// \name Properties + /// @{ /// /// \returns The size of the string excluding null terminator @@ -180,17 +221,24 @@ public: } /// - /// \returns \f$true\f$ if the string contains no characters, \f$false\f$ otherwise. + /// \returns \emph{true} if the string contains no characters, \emph{false} otherwise. constexpr bool is_empty() const { return size() == 0; } + /// @} + + // Access ============================================================================================================== +public: + + /// \name Access + /// @{ /// /// \brief Array Access Operator /// \param i the index to access - /// \returns a reference to the wchar_tacter + /// \returns a reference to the character constexpr wchar_t& operator[](size_t i) { return _str[i]; } @@ -198,7 +246,7 @@ public: /// /// \brief Const-Array Access Operator /// \param i the index to access - /// \returns a copy of the wchar_tacter + /// \returns a copy of the character constexpr const wchar_t& operator[](size_t i) const { return _str[i]; } @@ -221,7 +269,14 @@ public: return _str; } + /// @} + + // Examination ========================================================================================================= +public: + + /// \name Examination + /// @{ /// /// \returns The length of the string to the first null-terminator @@ -231,7 +286,7 @@ public: /// /// \param str the string to compare against - /// \param i An offset to start with in \f$this\f$ + /// \param i An offset to start with in \emph{this} /// \param n The number of characters to compare /// \returns Zero if both strings are equal, otherwise a negative value if lhs appears before rhs according to the /// current locale, otherwise a positive value. @@ -247,7 +302,7 @@ public: /// /// \brief String Comparison /// \param str the string to compare against - /// \param i An offset to start at in \f$this\f$ + /// \param i An offset to start at in \emph{this} /// \param n The number of characters to compare /// \returns Zero if both strings are equal, otherwise a negative value if lhs appears before rhs according to the /// current locale, otherwise a positive value. @@ -278,17 +333,17 @@ public: /// /// \brief Check if the string contains a character /// \param c The character to find - /// \param i An offset to start at in \f$this\f$ - /// \returns \f$true\f$ if \f$c\f$ is contained in \f$this\f$ - constexpr bool contains(char c, size_t i = 0) const { + /// \param i An offset to start at in \emph{this} + /// \returns \emph{true} if \emph{c} is contained in \emph{this} + constexpr bool contains(wchar_t c, size_t i = 0) const { return find(c, i) != size(); } /// - /// \brief Finds the index of the first occurrence of \f$c\f$ in the string - /// \param c the wchar_tacter to find - /// \param i An offset to start at in \f$this\f$ - /// \returns The index of \f$c\f$ if it occurs in the string, otherwise returns `size()` + /// \brief Finds the index of the first occurrence of \emph{c} in the string + /// \param c the character to find + /// \param i An offset to start at in \emph{this} + /// \returns The index of \emph{c} if it occurs in the string, otherwise returns `size()` constexpr size_t find(wchar_t c, size_t i = 0) const { if (i >= size()) { // bounds check return size(); @@ -299,24 +354,24 @@ public: } /// - /// \brief Finds the index of the first occurrence of \f$str\f$ in the string. + /// \brief Finds the index of the first occurrence of \emph{str} in the string. /// \param str the string to find - /// \param i An offset to start at in \f$this\f$ - /// \returns The index of \f$str\f$ if it occurs in the string, otherwise returns `size()` + /// \param i An offset to start at in \emph{this} + /// \returns The index of \emph{str} if it occurs in the string, otherwise returns `size()` constexpr size_t find(const _wstring& str, size_t i = 0) const { // bounds check if (i >= size()) { // bounds check return size(); } - const wchar_t* loc = ::wcsstr(_str, str); + const wchar_t* loc = ::wcsstr(_str, str._str); return loc ? loc - _str : size(); } /// - /// \brief Finds the index of the first occurrence of \f$str\f$ in the string. + /// \brief Finds the index of the first occurrence of \emph{str} in the string. /// \param str the string to find - /// \param i An offset to start at in \f$this\f$ - /// \returns The index of \f$str\f$ if it occurs in the string, otherwise returns `size()` + /// \param i An offset to start at in \emph{this} + /// \returns The index of \emph{str} if it occurs in the string, otherwise returns `size()` constexpr size_t find(const wcstring& str, size_t i = 0) const { if (i + str.size() > size()) { // bounds check return size(); @@ -327,10 +382,10 @@ public: } /// - /// \brief Finds the index of the last occurrence of \f$c\f$ in the string. + /// \brief Finds the index of the last occurrence of \emph{c} in the string. /// \param c the string to find - /// \param i An offset to start at in \f$this\f$ - /// \returns The index of \f$c\f$ if it occurs in the string, otherwise returns `size()` + /// \param i An offset to start at in \emph{this} + /// \returns The index of \emph{c} if it occurs in the string, otherwise returns `size()` constexpr size_t rfind(wchar_t c, size_t i = npos) const { if (size() == 0) { return size(); @@ -345,10 +400,10 @@ public: } /// - /// \brief Finds the index of the last occurrence of \f$str\f$ in the string. + /// \brief Finds the index of the last occurrence of \emph{str} in the string. /// \param str the string to find - /// \param i An offset to start at in \f$this\f$ - /// \returns The index of \f$str\f$ if it occurs in the string, otherwise returns `size()` + /// \param i An offset to start at in \emph{this} + /// \returns The index of \emph{str} if it occurs in the string, otherwise returns `size()` constexpr size_t rfind(const wcstring& str, size_t i = npos) const { if (size() == 0) { return size(); @@ -366,11 +421,11 @@ public: } /// - /// \brief Finds the index of the last occurrence of \f$str\f$ in the string. + /// \brief Finds the index of the last occurrence of \emph{str} in the string. /// \param str the string to find - /// \param i An offset to start at in \f$this\f$ - /// \returns The index of \f$str\f$ if it occurs in the string, otherwise returns `size()` - constexpr size_t rfind(const string& str, size_t i = npos) const { + /// \param i An offset to start at in \emph{this} + /// \returns The index of \emph{str} if it occurs in the string, otherwise returns `size()` + constexpr size_t rfind(const _wstring& str, size_t i = npos) const { if (size() == 0) { return size(); } @@ -388,27 +443,32 @@ public: /// /// \brief Retrieve a substring of a string - /// \param i An offset to start at in \f$this\f$ + /// \param i An offset to start at in \emph{this} /// \param n the number of characters - /// \returns A new string containing the range of characters specified by \f$i\f$ and \f$n\f$ + /// \returns A new string containing the range of characters specified by \emph{i} and \emph{n} constexpr _wstring substring(size_t i, size_t n = npos) const { - if (i >= size()) { + if (i >= size() || n == 0) { return _wstring(""); } n = fennec::min(n, size() - i); _wstring res; res._str.allocate(n + 1); - fennec::wmemcpy(res.data(), _str + i, n); + fennec::memcpy(res.data(), _str + i, n); return res; } + /// @} // Modifiers =========================================================================================================== +public: + + /// \name Modifiers + /// @{ /// /// \brief String Resize - /// \brief Resizes the underlying allocation to hold \f$n\f$ characters and a null terminator. + /// \brief Resizes the underlying allocation to hold \emph{n} characters and a null terminator. /// \param n The new size of the string constexpr void resize(size_t n) { _str.reallocate(n + 1); @@ -418,14 +478,14 @@ public: /// /// \brief Character Append /// \param c A character to append - /// \returns A new string containing the previous contents and an additional character \f$c\f$. + /// \returns A new string containing the previous contents and an additional character \emph{c}. constexpr _wstring operator+(wchar_t c) const { if (_str == nullptr) { return _wstring(1, c); } _wstring res; res._str.allocate(capacity() + 1); - fennec::wmemcpy(res.data(), _str, size()); + fennec::memcpy(res.data(), _str, size()); res[size()] = c; return res; } @@ -433,30 +493,32 @@ public: /// /// \brief Character Prepend /// \param c A character to append - /// \returns A new string containing the character \f$c\f$ followed by the previous contents. + /// \returns A new string containing the character \emph{c} followed by the previous contents. friend constexpr _wstring operator+(wchar_t c, const _wstring& str) { - _wstring res(1, c); - return res += str; + _wstring res(str.size() + 1); + res[0] = c; + fennec::memcpy(res.data() + 1, str.data(), str.size()); + return res; } /// /// \param cstr The string to append - /// \returns A new string containing the previous contents followed by the contents of \f$cstr\f$ + /// \returns A new string containing the previous contents followed by the contents of \emph{cstr} constexpr _wstring operator+(const wcstring& cstr) const { if (_str == nullptr) { return _wstring(cstr); } _wstring res; res._str.allocate(size() + cstr.size() + 1); - fennec::wmemcpy(res.data(), _str, size()); - fennec::wmemcpy(res.data() + size(), cstr, cstr.size()); + fennec::memcpy(res.data(), _str, size()); + fennec::memcpy(res.data() + size(), cstr, cstr.size()); return res; } /// /// \brief String Append /// \param str The string to append - /// \returns A new string containing the previous contents followed by the contents of \f$cstr\f$ + /// \returns A new string containing the previous contents followed by the contents of \emph{cstr} constexpr _wstring operator+(const _wstring& str) const { if (_str == nullptr) { return _wstring(str); @@ -466,15 +528,15 @@ public: } _wstring res; res._str.allocate(size() + str.size() + 1); - fennec::wmemcpy(res.data(), _str, size()); - fennec::wmemcpy(res.data() + size(), str.data(), str.size()); + fennec::memcpy(res.data(), _str, size()); + fennec::memcpy(res.data() + size(), str.data(), str.size()); return res; } /// /// \brief Character Append Assignment /// \param c A character to append - /// \returns \f$this\f$ string containing an additional character \f$c\f$. + /// \returns \emph{this} string containing an additional character \emph{c}. constexpr _wstring& operator+=(wchar_t c) { if (_str == nullptr) { _str.allocate(2); @@ -488,21 +550,21 @@ public: /// /// \param cstr The string to append - /// \returns \f$this\f$ string expanded to additionally contain \f$cstr\f$ + /// \returns \emph{this} string expanded to additionally contain \emph{cstr} constexpr _wstring& operator+=(const wcstring& cstr) { if (_str == nullptr) { return *this = cstr; } size_t middle = size(); _str.reallocate(middle + cstr.size() + 1); - fennec::wmemcpy(_str + middle, cstr, cstr.size()); + fennec::memcpy(_str + middle, cstr, cstr.size()); return *this; } /// /// \brief String Append Assignment /// \param str The string to append - /// \returns \f$this\f$ string expanded to additionally contain \f$str\f$ + /// \returns \emph{this} string expanded to additionally contain \emph{str} constexpr _wstring& operator+=(const _wstring& str) { if (_str == nullptr) { return *this = str; @@ -512,12 +574,18 @@ public: } size_t middle = size(); _str.reallocate(middle + str.size() + 1); - fennec::wmemcpy(_str + middle, str.data(), str.size()); + fennec::memcpy(_str + middle, str.data(), str.size()); return *this; } + /// @} - // Iteration =========================================================================================================== + +// Iteration =========================================================================================================== +public: + + /// \name Iteration + /// @{ /// /// \returns A pointer to the first character in the string. @@ -546,14 +614,18 @@ public: return _str.data() + _str.capacity(); } + /// @} + +// Private Member Variables ============================================================================================ private: alloc_t _str; }; -template<> -struct hash : hash { - constexpr size_t operator()(const string& str) const { +/// \brief Hashing for `fennec::wstring` +template +struct hash<_wstring> : hash { + constexpr size_t operator()(const _wstring& str) const { return hash::operator()(byte_array(str.data(), str.size())); } }; diff --git a/include/fennec/threading/atomic.h b/include/fennec/threading/atomic.h index 19839e3..f874ba9 100644 --- a/include/fennec/threading/atomic.h +++ b/include/fennec/threading/atomic.h @@ -62,16 +62,25 @@ public: // Definitions ========================================================================================================= public: - using value_t = T; + /// \name Definitions + /// @{ + + using value_t = T; //!< The type of the held atomic value + + /// @} // Constructors ======================================================================================================== +public: + + /// \name Constructors & Destructor + /// @{ /// /// \brief Default Constructor /// - /// \details Initializes the held atomic variable with \f$0\f$. + /// \details Initializes the held atomic variable with \math{0}. constexpr atomic() noexcept : _value(static_cast(0)) { } @@ -79,25 +88,29 @@ public: /// /// \brief Value Constructor /// - /// \details Initializes the held atomic variable with \f$value\f$. + /// \details Initializes the held atomic variable with \emph{value}. /// \param value The value to initialize the atomic variable with. constexpr atomic(const T value) noexcept : _value(value) { } + /// + /// \brief Copy Constructor + /// \details Deleted, copying atomics is not allowed. atomic(const atomic&) = delete; + /// @} // Assignment ========================================================================================================== - atomic& operator=(const atomic&) = delete; - atomic& operator=(const atomic&) volatile = delete; + /// \name Assignment + /// @{ /// - /// \details Atomically assigns \f$x\f$ to the atomic variable. + /// \details Atomically assigns \emph{x} to the atomic variable. /// \param x The value to assign - /// \returns \f$x\f$ + /// \returns \emph{x} T operator=(const T x) noexcept { this->store(x); return x; @@ -106,57 +119,35 @@ public: /// /// \brief Stores a value into an atomic object /// - /// \details Atomically assigns \f$x\f$ to the atomic variable. + /// \details Atomically assigns \emph{x} to the atomic variable. /// \param x The value to assign - /// \returns \f$x\f$ + /// \returns \emph{x} T operator=(const T x) volatile noexcept { this->store(x); return x; } - - -// Modifiers =========================================================================================================== + /// + /// \brief Copy Assignment + /// \details Deleted, copying atomics is not allowed. + /// \returns Deleted + atomic& operator=(const atomic&) = delete; /// - /// \details Atomically replaces the current value with \f$x\f$. Memory is affected according to the value of \f$order\f$. - /// \param x The value to store into the atomic variable - /// \param order Memory order constraints to enforce - void store(const T x, memory_order order = memory_order_seq_cst) noexcept { - ::atomic_store_explicit(&_value, x, order); - } + /// \brief Copy Assignment + /// \details Deleted, copying atomics is not allowed. + /// \returns Deleted + atomic& operator=(const atomic&) volatile = delete; - /// - /// \brief Atomically replaces the value of the atomic object with a non-atomic argument - /// - /// \details Atomically replaces the current value with \f$x\f$. Memory is affected according to the value of \f$order\f$. - /// \param x The value to store into the atomic variable - /// \param order Memory order constraints to enforce - void store(const T x, memory_order order = memory_order_seq_cst) volatile noexcept { - ::atomic_store_explicit(&_value, x, order); - } + /// @} - /// - /// \details Atomically loads and returns the current value of the atomic variable. - /// Memory is affected according to the value of \f$order\f$. - /// \param order Memory order constraints to enforce - /// \returns The current value of the atomic variable. - T load(memory_order order = memory_order_seq_cst) const noexcept { - return ::atomic_load_explicit(&_value, order); - } - /// - /// \brief Atomically obtains the value of the atomic object - /// - /// \details Atomically loads and returns the current value of the atomic variable. - /// Memory is affected according to the value of \f$order\f$. - /// \param order Memory order constraints to enforce - /// \returns The current value of the atomic variable. - T load(memory_order order = memory_order_seq_cst) const volatile noexcept { - return ::atomic_load_explicit(&_value, order); - } +// Access ============================================================================================================== +public: + /// \name Access + /// @{ /// /// \details Atomically loads and returns the current value of the atomic variable. Equivalent to `load()`. @@ -172,10 +163,59 @@ public: return load(); } + /// @} + + + +// Modifiers =========================================================================================================== +public: + + /// \name Modifiers + /// @{ /// - /// \details Atomically replaces the underlying value with \f$x\f$ (a read-modify-write operation). - /// Memory is affected according to the value of \f$order\f$. + /// \details Atomically replaces the current value with \emph{x}. Memory is affected according to the value of \emph{order}. + /// \param x The value to store into the atomic variable + /// \param order Memory order constraints to enforce + void store(const T x, memory_order order = memory_order_seq_cst) noexcept { + ::atomic_store_explicit(&_value, x, order); + } + + /// + /// \brief Atomically replaces the value of the atomic object with a non-atomic argument + /// + /// \details Atomically replaces the current value with \emph{x}. Memory is affected according to the value of \emph{order}. + /// \param x The value to store into the atomic variable + /// \param order Memory order constraints to enforce + void store(const T x, memory_order order = memory_order_seq_cst) volatile noexcept { + ::atomic_store_explicit(&_value, x, order); + } + + + /// + /// \details Atomically loads and returns the current value of the atomic variable. + /// Memory is affected according to the value of \emph{order}. + /// \param order Memory order constraints to enforce + /// \returns The current value of the atomic variable. + T load(memory_order order = memory_order_seq_cst) const noexcept { + return ::atomic_load_explicit(&_value, order); + } + + /// + /// \brief Atomically obtains the value of the atomic object + /// + /// \details Atomically loads and returns the current value of the atomic variable. + /// Memory is affected according to the value of \emph{order}. + /// \param order Memory order constraints to enforce + /// \returns The current value of the atomic variable. + T load(memory_order order = memory_order_seq_cst) const volatile noexcept { + return ::atomic_load_explicit(&_value, order); + } + + + /// + /// \details Atomically replaces the underlying value with \emph{x} (a read-modify-write operation). + /// Memory is affected according to the value of \emph{order}. /// \param x Value to assign /// \param order Memory order constraints to enforce /// \return The value of the atomic variable before the call. @@ -186,8 +226,8 @@ public: /// /// \brief Atomically replaces the value of the atomic object and obtains the value held previously /// - /// \details Atomically replaces the underlying value with \f$x\f$ (a read-modify-write operation). - /// Memory is affected according to the value of \f$order\f$. + /// \details Atomically replaces the underlying value with \emph{x} (a read-modify-write operation). + /// Memory is affected according to the value of \emph{order}. /// \param x Value to assign /// \param order Memory order constraints to enforce /// \return The value of the atomic variable before the call. @@ -197,39 +237,39 @@ public: /// - /// \details Atomically compares the value of `*this` with that of \f$exp\f$. - /// If they are equal, replaces the former with \f$x\f$ (performs read-modify-write operation). - /// Otherwise, loads the actual value stored in *this into \f$exp\f$ (performs load operation). + /// \details Atomically compares the value of `*this` with that of \emph{exp}. + /// If they are equal, replaces the former with \emph{x} (performs read-modify-write operation). + /// Otherwise, loads the actual value stored in *this into \emph{exp} (performs load operation). /// \param exp Reference to the value expected to be found in the atomic object. /// \param x The value to store in the atomic object if it is as expected. /// \param succ The memory synchronization ordering for the read-modify-write operation if the comparison succeeds. /// \param fail The memory synchronization ordering for the load operation if the comparison fails. - /// \returns \f$true\f$ if the underlying atomic value was successfully changed, \f$false\f$ otherwise. + /// \returns \emph{true} if the underlying atomic value was successfully changed, \emph{false} otherwise. bool compare_exchange_weak(T& exp, T x, memory_order succ, memory_order fail) noexcept { return ::atomic_compare_exchange_weak_explicit(&_value, &exp, x, succ, fail); } /// - /// \details Atomically compares the value of `*this` with that of \f$exp\f$. - /// If they are equal, replaces the former with \f$x\f$ (performs read-modify-write operation). - /// Otherwise, loads the actual value stored in *this into \f$exp\f$ (performs load operation). + /// \details Atomically compares the value of `*this` with that of \emph{exp}. + /// If they are equal, replaces the former with \emph{x} (performs read-modify-write operation). + /// Otherwise, loads the actual value stored in *this into \emph{exp} (performs load operation). /// \param exp Reference to the value expected to be found in the atomic object. /// \param x The value to store in the atomic object if it is as expected. /// \param succ The memory synchronization ordering for the read-modify-write operation if the comparison succeeds. /// \param fail The memory synchronization ordering for the load operation if the comparison fails. - /// \returns \f$true\f$ if the underlying atomic value was successfully changed, \f$false\f$ otherwise. + /// \returns \emph{true} if the underlying atomic value was successfully changed, \emph{false} otherwise. bool compare_exchange_weak(T& exp, T x, memory_order succ, memory_order fail) volatile noexcept { return ::atomic_compare_exchange_weak_explicit(&_value, &exp, x, succ, fail); } /// - /// \details Atomically compares the value of `*this` with that of \f$exp\f$. - /// If they are equal, replaces the former with \f$x\f$ (performs read-modify-write operation). - /// Otherwise, loads the actual value stored in *this into \f$exp\f$ (performs load operation). + /// \details Atomically compares the value of `*this` with that of \emph{exp}. + /// If they are equal, replaces the former with \emph{x} (performs read-modify-write operation). + /// Otherwise, loads the actual value stored in *this into \emph{exp} (performs load operation). /// \param exp Reference to the value expected to be found in the atomic object. /// \param x The value to store in the atomic object if it is as expected. /// \param order The memory synchronization ordering for both operations. - /// \returns \f$true\f$ if the underlying atomic value was successfully changed, \f$false\f$ otherwise. + /// \returns \emph{true} if the underlying atomic value was successfully changed, \emph{false} otherwise. bool compare_exchange_weak(T& exp, T x, memory_order order = memory_order_seq_cst) noexcept { return ::atomic_compare_exchange_weak_explicit(&_value, &exp, x, order, order); } @@ -237,52 +277,52 @@ public: /// /// \brief Atomically compares the value of the atomic object with non-atomic argument and performs atomic exchange if equal or atomic load if not /// - /// \details Atomically compares the value of `*this` with that of \f$exp\f$. - /// If they are equal, replaces the former with \f$x\f$ (performs read-modify-write operation). - /// Otherwise, loads the actual value stored in *this into \f$exp\f$ (performs load operation). + /// \details Atomically compares the value of `*this` with that of \emph{exp}. + /// If they are equal, replaces the former with \emph{x} (performs read-modify-write operation). + /// Otherwise, loads the actual value stored in *this into \emph{exp} (performs load operation). /// \param exp Reference to the value expected to be found in the atomic object. /// \param x The value to store in the atomic object if it is as expected. /// \param order The memory synchronization ordering for both operations. - /// \returns \f$true\f$ if the underlying atomic value was successfully changed, \f$false\f$ otherwise. + /// \returns \emph{true} if the underlying atomic value was successfully changed, \emph{false} otherwise. bool compare_exchange_weak(T& exp, T x, memory_order order = memory_order_seq_cst) volatile noexcept { return ::atomic_compare_exchange_weak_explicit(&_value, &exp, x, order, order); } /// - /// \details Atomically compares the value of `*this` with that of \f$exp\f$. - /// If they are equal, replaces the former with \f$x\f$ (performs read-modify-write operation). - /// Otherwise, loads the actual value stored in *this into \f$exp\f$ (performs load operation). + /// \details Atomically compares the value of `*this` with that of \emph{exp}. + /// If they are equal, replaces the former with \emph{x} (performs read-modify-write operation). + /// Otherwise, loads the actual value stored in *this into \emph{exp} (performs load operation). /// \param exp Reference to the value expected to be found in the atomic object. /// \param x The value to store in the atomic object if it is as expected. /// \param succ The memory synchronization ordering for the read-modify-write operation if the comparison succeeds. /// \param fail The memory synchronization ordering for the load operation if the comparison fails. - /// \returns \f$true\f$ if the underlying atomic value was successfully changed, \f$false\f$ otherwise. + /// \returns \emph{true} if the underlying atomic value was successfully changed, \emph{false} otherwise. bool compare_exchange_strong(T& exp, T x, memory_order succ, memory_order fail) noexcept { return ::atomic_compare_exchange_strong_explicit(&_value, &exp, x, succ, fail); } /// - /// \details Atomically compares the value of `*this` with that of \f$exp\f$. - /// If they are equal, replaces the former with \f$x\f$ (performs read-modify-write operation). - /// Otherwise, loads the actual value stored in *this into \f$exp\f$ (performs load operation). + /// \details Atomically compares the value of `*this` with that of \emph{exp}. + /// If they are equal, replaces the former with \emph{x} (performs read-modify-write operation). + /// Otherwise, loads the actual value stored in *this into \emph{exp} (performs load operation). /// \param exp Reference to the value expected to be found in the atomic object. /// \param x The value to store in the atomic object if it is as expected. /// \param succ The memory synchronization ordering for the read-modify-write operation if the comparison succeeds. /// \param fail The memory synchronization ordering for the load operation if the comparison fails. - /// \returns \f$true\f$ if the underlying atomic value was successfully changed, \f$false\f$ otherwise. + /// \returns \emph{true} if the underlying atomic value was successfully changed, \emph{false} otherwise. bool compare_exchange_strong(T& exp, T x, memory_order succ, memory_order fail) volatile noexcept { return ::atomic_compare_exchange_strong_explicit(&_value, &exp, x, succ, fail); } /// - /// \details Atomically compares the value of `*this` with that of \f$exp\f$. - /// If they are equal, replaces the former with \f$x\f$ (performs read-modify-write operation). - /// Otherwise, loads the actual value stored in *this into \f$exp\f$ (performs load operation). + /// \details Atomically compares the value of `*this` with that of \emph{exp}. + /// If they are equal, replaces the former with \emph{x} (performs read-modify-write operation). + /// Otherwise, loads the actual value stored in *this into \emph{exp} (performs load operation). /// \param exp Reference to the value expected to be found in the atomic object. /// \param x The value to store in the atomic object if it is as expected. /// \param order The memory synchronization ordering for both operations. - /// \returns \f$true\f$ if the underlying atomic value was successfully changed, \f$false\f$ otherwise. + /// \returns \emph{true} if the underlying atomic value was successfully changed, \emph{false} otherwise. bool compare_exchange_strong(T& exp, T x, memory_order order = memory_order_seq_cst) noexcept { return ::atomic_compare_exchange_strong_explicit(&_value, &exp, x, order, order); } @@ -290,149 +330,268 @@ public: /// /// \brief Atomically compares the value of the atomic object with non-atomic argument and performs atomic exchange if equal or atomic load if not /// - /// \details Atomically compares the value of `*this` with that of \f$exp\f$. - /// If they are equal, replaces the former with \f$x\f$ (performs read-modify-write operation). - /// Otherwise, loads the actual value stored in *this into \f$exp\f$ (performs load operation). + /// \details Atomically compares the value of `*this` with that of \emph{exp}. + /// If they are equal, replaces the former with \emph{x} (performs read-modify-write operation). + /// Otherwise, loads the actual value stored in *this into \emph{exp} (performs load operation). /// \param exp Reference to the value expected to be found in the atomic object. /// \param x The value to store in the atomic object if it is as expected. /// \param order The memory synchronization ordering for both operations. - /// \returns \f$true\f$ if the underlying atomic value was successfully changed, \f$false\f$ otherwise. + /// \returns \emph{true} if the underlying atomic value was successfully changed, \emph{false} otherwise. bool compare_exchange_strong(T& exp, T x, memory_order order = memory_order_seq_cst) volatile noexcept { return ::atomic_compare_exchange_strong_explicit(&_value, &exp, x, order, order); } + /// @} + // Operations ========================================================================================================== +public: + /// \name Operations + /// @{ + + /// + /// \param x The value to add. + /// \param order The memory order to abide by. + /// \returns The value previously held by the atomic. T fetch_add(const T x, memory_order order = memory_order_seq_cst) noexcept { return ::atomic_fetch_add_explicit(&_value, x, order); } + /// + /// \brief Atomically add a value and return the previously held value. + /// \param x The value to add. + /// \param order The memory order to abide by. + /// \returns The value previously held by the atomic. T fetch_add(const T x, memory_order order = memory_order_seq_cst) volatile noexcept { return ::atomic_fetch_add_explicit(&_value, x, order); } + + /// + /// \param x The value to add. + /// \returns The result of the addition. T operator+=(const T x) noexcept { return this->fetch_add(x) + x; } + /// + /// \brief Atomically add a value and return the result. + /// \param x The value to add. + /// \returns The result of the addition. T operator+=(const T x) volatile noexcept { return this->fetch_add(x) + x; } - + /// + /// \returns The held value incremented by 1 T operator++() noexcept { return this->fetch_add(1) + 1; } + /// + /// \brief Post-Increment + /// \returns The held value incremented by 1 T operator++() volatile noexcept { return this->fetch_add(1) + 1; } + + /// + /// \returns The previously held value before the increment. T operator++(int) noexcept { return this->fetch_add(1); } + /// + /// \brief Pre-Increment + /// \returns The previously held value before the increment. T operator++(int) volatile noexcept { return this->fetch_add(1); } - + + /// + /// \param x The value to subtract. + /// \param order The memory order to abide by. + /// \returns The value previously held by the atomic. T fetch_sub(const T x, memory_order order = memory_order_seq_cst) noexcept { return ::atomic_fetch_sub_explicit(&_value, x, order); } + /// + /// \brief Atomically subtract a value and return the previously held value. + /// \param x The value to subtract. + /// \param order The memory order to abide by. + /// \returns The value previously held by the atomic. T fetch_sub(const T x, memory_order order = memory_order_seq_cst) volatile noexcept { return ::atomic_fetch_sub_explicit(&_value, x, order); } + + /// + /// \param x The value to subtract. + /// \returns The result of the subtraction. T operator-=(const T x) noexcept { return this->fetch_sub(x) - x; } + /// + /// \brief Atomically subtract a value and return the result. + /// \param x The value to subtract. + /// \returns The result of the addition. T operator-=(const T x) volatile noexcept { return this->fetch_sub(x) - x; } - + /// + /// \returns The held value decremented by 1 T operator--() noexcept { return this->fetch_sub(1) - 1; } + /// + /// \brief Post-Decrement + /// \returns The held value decremented by 1 T operator--() volatile noexcept { return this->fetch_sub(1) - 1; } + + /// + /// \returns The previously held value before the decrement. T operator--(int) noexcept { return this->fetch_sub(1); } + /// + /// \brief Pre-Decrement + /// \returns The previously held value before the decrement. T operator--(int) volatile noexcept { return this->fetch_sub(1); } + /// @} -// Bit Operations ====================================================================================================== +// Bit-Wise Operations ================================================================================================= + + /// \name Bit-Wise Operations + /// @{ + + + /// + /// \param x The value to and against. + /// \param order The memory order to abide by. + /// \returns The value previously held by the atomic. T fetch_and(const T x, memory_order order = memory_order_seq_cst) noexcept requires is_integral_v { return ::atomic_fetch_and_explicit(&_value, x, order); } + /// + /// \brief Atomically perform a bit-wise and with a value and return the previously held value. + /// \param x The value to and against. + /// \param order The memory order to abide by. + /// \returns The value previously held by the atomic. T fetch_and(const T x, memory_order order = memory_order_seq_cst) volatile noexcept requires is_integral_v { return ::atomic_fetch_and_explicit(&_value, x, order); } + + /// + /// \param x The value to and against. + /// \returns The result of the operation. T operator&=(const T x) noexcept requires is_integral_v { return this->fetch_and(x) & x; } + /// + /// \param x The value to and against. + /// \brief Atomically perform a bit-wise and with a value and return the result. + /// \returns The result of the operation. T operator&=(const T x) volatile noexcept requires is_integral_v { return this->fetch_and(x) & x; } + /// + /// \param x The value to or with. + /// \param order The memory order to abide by. + /// \returns The value previously held by the atomic. T fetch_or(const T x, memory_order order = memory_order_seq_cst) noexcept requires is_integral_v { return ::atomic_fetch_or_explicit(&_value, x, order); } + /// + /// \brief Atomically perform a bit-wise or with a value and return the previously held value. + /// \param x The value to or with. + /// \param order The memory order to abide by. + /// \returns The value previously held by the atomic. T fetch_or(const T x, memory_order order = memory_order_seq_cst) volatile noexcept requires is_integral_v { return ::atomic_fetch_or_explicit(&_value, x, order); } + + /// + /// \param x The value to or with. + /// \returns The result of the operation. T operator|=(const T x) noexcept requires is_integral_v { return this->fetch_or(x) & x; } + /// + /// \param x The value to or with. + /// \brief Atomically perform a bit-wise or with a value and return the result. + /// \returns The result of the operation. T operator|=(const T x) volatile noexcept requires is_integral_v { return this->fetch_or(x) & x; } + /// + /// \param x The value to xor with. + /// \param order The memory order to abide by. + /// \returns The value previously held by the atomic. T fetch_xor(const T x, memory_order order = memory_order_seq_cst) noexcept requires is_integral_v { return ::atomic_fetch_xor_explicit(&_value, x, order); } + /// + /// \brief Atomically perform a bit-wise xor with a value and return the previously held value. + /// \param x The value to xor with. + /// \param order The memory order to abide by. + /// \returns The value previously held by the atomic. T fetch_xor(const T x, memory_order order = memory_order_seq_cst) volatile noexcept requires is_integral_v { return ::atomic_fetch_xor_explicit(&_value, x, order); } + + /// + /// \param x The value to xor with. + /// \returns The result of the operation. T operator^=(const T x) noexcept requires is_integral_v { return this->fetch_xor(x) & x; } + /// + /// \param x The value to xor with. + /// \brief Atomically perform a bit-wise xor with a value and return the result. + /// \returns The result of the operation. T operator^=(const T x) volatile noexcept requires is_integral_v { return this->fetch_xor(x) & x; } + /// @} +// Private Member Variables ============================================================================================ private: _Atomic T _value; }; diff --git a/include/fennec/threading/detail/_atomic.h b/include/fennec/threading/detail/_atomic.h index 6f58d16..bce8592 100644 --- a/include/fennec/threading/detail/_atomic.h +++ b/include/fennec/threading/detail/_atomic.h @@ -25,7 +25,7 @@ #endif #define _Atomic volatile -#if FENNEC_COMPILER_GCC +#if FENNEC_GLIBC // memory_order ======================================================================================================== diff --git a/include/fennec/threading/lock_guard.h b/include/fennec/threading/lock_guard.h index 3c80bb3..1245388 100644 --- a/include/fennec/threading/lock_guard.h +++ b/include/fennec/threading/lock_guard.h @@ -35,20 +35,40 @@ namespace fennec { +/// +/// \brief RAII Implementation for Scope Locking of Mutexes +/// \tparam MutexT The mutex type. template class lock_guard { -public: - lock_guard() = delete; +// Constructors & Destructor =========================================================================================== +public: + + /// \name Constructors & Destructor + /// @{ + + // + + /// + /// \brief Guard Constructor + /// \param mutex The mutex to lock + /// \details Creates a lock on \emph{mutex} explicit lock_guard(MutexT& mutex) : mutex(mutex) { mutex.lock(); } + /// + /// \brief Destructor + /// \details Releases the lock on the mutex. ~lock_guard() { mutex.unlock(); } + /// @} + + +// Private Member Variables ============================================================================================ private: MutexT& mutex; }; diff --git a/include/fennec/threading/mpscq.h b/include/fennec/threading/mpscq.h index 7d838f2..f799e28 100644 --- a/include/fennec/threading/mpscq.h +++ b/include/fennec/threading/mpscq.h @@ -49,8 +49,14 @@ template struct mpscq { // Definitions ========================================================================================================= public: - using value_t = TypeT; - using elem_t = atomic; + + /// \name Definitions + /// @{ + + using value_t = TypeT; //!< The value type + using elem_t = atomic; //!< The element type + + /// @} private: using table_t = allocation; @@ -59,14 +65,33 @@ private: // Constructors & Destructor =========================================================================================== public: - mpscq() = delete; + /// \name Constructors & Destructor + /// @{ + + /// + /// \brief Queue Constructor + /// \param cap The capacity of the queue + /// \details This style of queue requires a fixed capacity. Make sure you allocate enough mpscq(size_t cap) : _data(cap) , _head(0), _count(0) , _tail(0) { } + /// + /// \brief Move Constructor + /// \param queue The queue to take ownership of. + mpscq(mpscq&& queue) + : _data(queue._data) + , _head(queue._head.load()) + , _count(queue._count.load()) + , _tail(queue._tail) { + } + + /// + /// \brief Queue Destructor + /// \details Releases the held queue. ~mpscq() { for (TypeT* it : _data) { unique_ptr ptr(it); @@ -74,64 +99,118 @@ public: _data.deallocate(); } + /// + /// \brief Default Constructor + /// \details Deleted, mspcq must be initialized with a capacity. + mpscq() = delete; + + /// + /// \brief Copy Constructor + /// \details Deleted, copying a mspcq is not allowed mpscq(const mpscq&) = delete; + /// @} + // Properties ========================================================================================================== +public: + /// \name Properties + /// @{ + + /// + /// \returns The current size of the queue. size_t size() const { return _count.load(memory_order_relaxed); } + /// + /// \returns The capacity of the queue. size_t capacity() const { return _data.capacity(); } + /// + /// \returns \emph{true} if the queue is empty, \emph{false} otherwise. bool is_empty() const { return size() == 0; } + /// @} + // Producers =========================================================================================================== + /// \name Producers + /// @{ + + /// + /// \param x The value to push. + /// \returns \emph{true} on success, \emph{false} on fail. bool push(const TypeT& x) { return this->_push(x); } + /// + /// \brief Push an element to the queue. + /// \param x The value to push. + /// \returns \emph{true} on success, \emph{false} on fail. bool push(TypeT&& x) noexcept { return this->_push(fennec::forward(x)); } + /// + /// \brief Emplace an element in the queue. + /// \tparam ArgsT The argument types. + /// \param args The arguments to construct the element with. + /// \returns \emph{true} on success, \emph{false} on fail. template bool emplace(ArgsT&&...args) { return this->_push(fennec::forward(args)...); } + /// @} + // Consumers =========================================================================================================== + /// \name Consumers + /// @{ + + /// + /// \brief Pop an element from the queue. + /// \returns A unique pointer to the popped value. + /// \note This function should only be called on one thread. unique_ptr pop() { unique_ptr res(_data[_tail].exchange(nullptr, memory_order_acquire)); if (not res) { return nullptr; } _tail = (_tail + 1) % _data.capacity(); - size_t r = _count.fetch_sub(1, memory_order_release); + const size_t r = _count.fetch_sub(1, memory_order_release); assertf(r > 0, "Popped element from empty queue!"); return fennec::move(res); } + /// @} + + +// Private Member Variables ============================================================================================ private: table_t _data; counter_t _head, _count; size_t _tail; + +// Private Helpers ===================================================================================================== +private: + template bool _push(ArgsT&&...args) { unique_ptr ptr = fennec::make_unique(fennec::forward(args)...); - size_t cap = _data.capacity(); - size_t ct = _count.fetch_add(1, memory_order_acquire); + const size_t cap = _data.capacity(); + const size_t ct = _count.fetch_add(1, memory_order_acquire); if (ct >= cap) { _count.fetch_sub(1, memory_order_release); return false; diff --git a/include/fennec/threading/mutex.h b/include/fennec/threading/mutex.h index 7ae4362..a1c4824 100644 --- a/include/fennec/threading/mutex.h +++ b/include/fennec/threading/mutex.h @@ -40,38 +40,100 @@ namespace fennec { +/// +/// \brief Basic Mutual Exclusion Support Class class mutex { + +// Definitions ========================================================================================================= public: + + /// \name Definitions + /// @{ + using handle_t = pthread_mutex_t; + /// @} + + +// Constructors & Destructors ========================================================================================== +public: + + /// \name Constructors & Destructor + /// @{ + + /// + /// \brief Mutex Constructor + /// \details Initializes a mutex handle. mutex() : _handle() { assertf((pthread_mutex_init(&_handle, nullptr) == 0), "Failed to initialize mutex.") } + + /// + /// \brief Mutex Destructor + /// \details Cleans up the underlying handle. ~mutex() { assertf((pthread_mutex_destroy(&_handle) == 0), "Failed to destroy mutex."); } + /// + /// \brief Copy Constructor + /// \details Deleted, no semantics for copying a mutex. mutex(const mutex&) = delete; + + /// @} + + +// Assignment ========================================================================================================== +public: + + /// \name Assignment + /// @{ + + /// + /// \brief Copy Assignment + /// \details Deleted, no semantics for copying a mutex. + /// \returns Deleted mutex& operator=(const mutex&) = delete; + /// @} + + +// Locking ============================================================================================================= +public: + + /// \name Locking + /// @{ + + /// + /// \brief Lock the mutex. + /// \details Blocks if unable to acquire lock. void lock() { assertf(pthread_mutex_lock(&_handle) == 0, "Error on lock()!"); } + /// + /// \brief Try locking the mutex. + /// \returns \emph{true} on success, \emph{false} otherwise. bool try_lock() { - int res = pthread_mutex_trylock(&_handle); + const int res = pthread_mutex_trylock(&_handle); assertf(res == EBUSY or res == 0, "Error on trylock()!"); return res == 0; } + /// + /// \brief Release the lock. + /// \details Asserts that the current thread does not hold a lock on the mutex. void unlock() { assertf(pthread_mutex_unlock(&_handle) == 0, "Error on unlock()!"); } + /// @} + + +// Private Member Variables ============================================================================================ private: - pthread_mutex_t _handle; - pthread_mutexattr_t _attr; + pthread_mutex_t _handle; }; } diff --git a/include/fennec/threading/thread.h b/include/fennec/threading/thread.h index 4f1a621..caa043c 100644 --- a/include/fennec/threading/thread.h +++ b/include/fennec/threading/thread.h @@ -52,29 +52,66 @@ private: static constexpr pthread_t nullthread = 0; public: + + /// \name Definitions + /// @{ + using handle_t = pthread_t; //!< The underlying handle type /// /// \brief Structure representing the id of a thread struct id { + + // Constructors & Destructor --------------------------------------------------------------------------------------- public: + + /// \name Constructor + /// @{ + /// - /// \brief Constructor + /// \brief Default Constructor + /// \details References a null thread. constexpr id() noexcept - : _id(0) { + : _id(nullthread) { } - constexpr friend bool operator==(id x, id y) noexcept { - if (x._id == 0) { - return y._id == 0; + /// + /// \brief Destructor + constexpr ~id() noexcept { + } + + /// @} + + + // Comparison ------------------------------------------------------------------------------------------------------ + public: + + /// + /// \brief Equality Operator + /// \param lhs Left-hand side of the operation + /// \param rhs Right-hand side of the operation + /// \returns \emph{true} if both ids represent the same thread, \emph{false} otherwise. + constexpr friend bool operator==(id lhs, id rhs) noexcept { + if (lhs._id == nullthread) { + return rhs._id == nullthread; } - if (y._id == 0) { + if (rhs._id == nullthread) { return false; } - return pthread_equal(x._id, y._id) != 0; + return pthread_equal(lhs._id, rhs._id) != 0; } - constexpr friend bool operator!=(id x, id y) noexcept { return !(x == y); } + /// + /// \brief Inequality Operator + /// \param lhs Left-hand side of the operation + /// \param rhs Right-hand side of the operation + /// \returns \emph{false} if both ids represent the same thread, \emph{true} otherwise. + constexpr friend bool operator!=(id lhs, id rhs) noexcept { + return !(lhs == rhs); + } + + + // Private Member Variables ---------------------------------------------------------------------------------------- private: friend class thread; friend struct hash; @@ -85,17 +122,42 @@ public: pthread_t _id; }; + /// @} + + +// Constructors & Destructor =========================================================================================== +public: + + /// \name Constructors & Destructor + /// @{ + + /// + /// \brief Default Constructor + /// \details Initializes a null thread. thread() noexcept : _handle(nullthread) { } - thread(thread&& th) + /// + /// \brief Move Constructor + /// \param th Thread to take ownership of. + thread(thread&& th) noexcept : _handle(th._handle) { th._handle = nullthread; } + /// + /// \brief Copy Constructor + /// \details Deleted, no semantics for copying a thread. thread(const thread&) = delete; + /// + /// \brief Thread Constructor + /// \tparam FuncT The function type + /// \tparam ArgsT The argument types + /// \param func The function to execute on the new thread + /// \param args The arguments to pass + /// \details Initializes a thread and runs \emph{func} with \emph{args...} template requires(not is_same_v>) thread(FuncT&& func, ArgsT&&...args) @@ -106,12 +168,33 @@ public: fennec::decay_copy(fennec::forward(args))... ); - int_t res = ::pthread_create(&_handle, nullptr, &detail::_run_thread, proxy.get()); + const int_t res = ::pthread_create(&_handle, nullptr, &detail::_run_thread, proxy.get()); assertf(res == 0, "Thread creation failed!"); proxy.release(); } + /// + /// \brief Thread Destructor + /// \details Attempts to join the thread, asserts if unable to. + ~thread() { + assertf(_handle == nullthread or joinable(), "Attempted to destruct a running thread!"); + join(); + } + + /// @} + + +// Assignment ========================================================================================================== +public: + + /// \name Assignment + /// @{ + + /// + /// \brief Move Assignment + /// \param th Thread to take ownership of. + /// \returns A reference to \emph{this} after taking ownership of \emph{th}. thread& operator=(thread&& th) noexcept { assertf(_handle == nullthread, "Attempted to overwrite running thread!"); @@ -121,52 +204,91 @@ public: return *this; } - ~thread() { - assertf(_handle == 0 or joinable(), "Attempted to destruct a running thread!"); - join(); - } + /// + /// \brief Deleted, no semantics for copying a thread. + thread& operator=(const thread&) = default; + /// @} + + +// Properties ========================================================================================================== +public: + + /// \name Properties + /// @{ + + /// + /// \brief Check if the thread is joinable. + /// \returns \math{\textbf{this}\neq\textbf{null} \& \textbf{this}\neq{p_{curr}}} bool joinable() const noexcept { return _handle != nullthread and pthread_self() != _handle; } + /// + /// \returns The id of the thread. + id get_id() const { + return _handle; + } + + /// + /// \returns The id of the current thread. + static id current() { + return pthread_self(); + } + + /// @} + + +// Operations ========================================================================================================== +public: + + /// \name Operations + /// @{ + + /// + /// \brief Join with this thread. + /// \details Blocks until this thread finishes its execution. void join() { if (not joinable()) { return; } - int_t res = pthread_join(_handle, nullptr); + const int_t res = pthread_join(_handle, nullptr); assertf(res == 0, "Failed to join thread!"); _handle = nullthread; } + /// + /// \brief Detatch this thread. + /// \details Separates the threads execution, releasing it. void detatch() { if (not joinable()) { return; } - int_t res = pthread_detach(_handle); + const int_t res = pthread_detach(_handle); assertf(res == 0, "Failed to detach thread!"); _handle = nullthread; } + /// + /// \brief Swap the held handles with \emph{other}. + /// \param other The thread to swap handles with. void swap(thread& other) { fennec::swap(_handle, other._handle); } - static id current() { - return pthread_self(); - } - + /// + /// \brief Relinquish execution. + /// \details This thread is pushed to the back of the CPU's scheduler queue. static void yield() { assertf(sched_yield() == 0, "Error yielding thread!"); } - id get_id() const { - return _handle; - } + /// @} +// Private Member Variables ============================================================================================ private: pthread_t _handle; }; diff --git a/metaprogramming/float.h b/metaprogramming/float.h index 2b4ec4e..d03b104 100644 --- a/metaprogramming/float.h +++ b/metaprogramming/float.h @@ -102,80 +102,80 @@ inline void float_h() out << "" << '\n'; - out << R"(/// \brief Does \f$float\f$ have an infinity?)" << '\n'; + out << R"(/// \brief Does \emph{float} have an infinity?)" << '\n'; out << "#define FLT_HAS_INFINITY " << std::dec << std::numeric_limits::has_infinity << '\n'; - out << R"(/// \brief Does \f$float\f$ have a quiet NaN?)" << '\n'; + out << R"(/// \brief Does \emph{float} have a quiet NaN?)" << '\n'; out << "#define FLT_HAS_QUIET_NAN " << std::dec << std::numeric_limits::has_quiet_NaN << '\n'; - out << R"(/// \brief Does \f$float\f$ have a signaling NaN?)" << '\n'; + out << R"(/// \brief Does \emph{float} have a signaling NaN?)" << '\n'; out << "#define FLT_HAS_SIGNALING_NAN " << std::dec << std::numeric_limits::has_signaling_NaN << '\n'; - out << R"(/// \brief Does \f$float\f$ use denormalization?)" << '\n'; + out << R"(/// \brief Does \emph{float} use denormalization?)" << '\n'; out << "#define FLT_HAS_DENORM " << std::dec << std::numeric_limits::has_denorm << '\n'; - out << R"(/// \brief Does \f$float\f$ have loss with denormalization?)" << '\n'; + out << R"(/// \brief Does \emph{float} have loss with denormalization?)" << '\n'; out << "#define FLT_HAS_DENORM_LOSS " << std::dec << std::numeric_limits::has_denorm_loss << '\n'; - out << R"(/// \brief What rounding style does \f$float\f$ use?)" << '\n'; + out << R"(/// \brief What rounding style does \emph{float} use?)" << '\n'; out << "#define FLT_ROUNDS " << std::dec << std::numeric_limits::round_style << '\n'; - out << R"(/// \brief Does \f$float\f$ use the IEEE floating point specification?)" << '\n'; + out << R"(/// \brief Does \emph{float} use the IEEE floating point specification?)" << '\n'; out << "#define FLT_IS_IEC559 " << std::dec << std::numeric_limits::is_iec559 << '\n'; - out << R"(/// \brief The number of mantissa bits in \f$float\f$.)" << '\n'; + out << R"(/// \brief The number of mantissa bits in \emph{float}.)" << '\n'; out << "#define FLT_MANT_DIG " << std::dec << std::numeric_limits::digits << '\n'; - out << R"(/// \brief The number of decimal digits guaranteed to be preserved in a \f$float\f$ → \f$text\f$ → \f$float\f$.)" << '\n'; + out << R"(/// \brief The number of decimal digits guaranteed to be preserved in a \emph{float} → \emph{text} → \emph{float}.)" << '\n'; out << "#define FLT_DIG " << std::dec << std::numeric_limits::digits10 << '\n'; - out << R"(/// \brief The decimal precision required to serialize and deserialize a \f$float\f$.)" << '\n'; + out << R"(/// \brief The decimal precision required to serialize and deserialize a \emph{float}.)" << '\n'; out << "#define FLT_DECIMAL_DIG " << std::dec << std::numeric_limits::max_digits10 << '\n'; - out << R"(/// \brief The radix, or integer base, used to represent a \f$float\f$.)" << '\n'; + out << R"(/// \brief The radix, or integer base, used to represent a \emph{float}.)" << '\n'; out << "#define FLT_RADIX " << std::dec << std::numeric_limits::radix << '\n'; - out << R"(/// \brief The minimum negative integer such that \f${FLT_RADIX}^{FLT_MIN_EXP}\f$ results in a normalized \f$float\f$.)" << '\n'; + out << R"(/// \brief The minimum negative integer such that \math{\textbf{FLT_RADIX}^\textbf{FLT_MIN_EXP}} results in a normalized \emph{float}.)" << '\n'; out << "#define FLT_MIN_EXP " << std::dec << std::numeric_limits::min_exponent << '\n'; - out << R"(/// \brief The maximum positive integer such that \f${FLT_RADIX}^{FLT_MAX_EXP}\f$ results in a non-infinite \f$float\f$.)" << '\n'; + out << R"(/// \brief The maximum positive integer such that \math{\textbf{FLT_RADIX}^\textbf{FLT_MAX_EXP}} results in a non-infinite \emph{float}.)" << '\n'; out << "#define FLT_MAX_EXP " << std::dec << std::numeric_limits::max_exponent << '\n'; - out << R"(/// \brief The minimum negative integer such that \f${10}^{FLT_MIN_EXP}\f$ results in a normalized \f$float\f$.)" << '\n'; + out << R"(/// \brief The minimum negative integer such that \math{{10}^\textbf{FLT_MIN_EXP}} results in a normalized \emph{float}.)" << '\n'; out << "#define FLT_MIN_10_EXP " << std::dec << std::numeric_limits::min_exponent10 << '\n'; - out << R"(/// \brief The maximum positive integer such that \f${10}^{FLT_MAX_EXP}\f$ results in a non-infinite \f$float\f$.)" << '\n'; + out << R"(/// \brief The maximum positive integer such that \math{{10}^\textbf{FLT_MAX_EXP}} results in a non-infinite \emph{float}.)" << '\n'; out << "#define FLT_MAX_10_EXP " << std::dec << std::numeric_limits::max_exponent10 << '\n'; - out << R"(/// \brief Do arithmetics operations with \f$float\f$ trap?)" << '\n'; + out << R"(/// \brief Do arithmetics operations with \emph{float} trap?)" << '\n'; out << "#define FLT_TRAPS " << std::dec << std::numeric_limits::traps << '\n'; - out << R"(/// \brief Do arithmetics operations with \f$float\f$ check for underflow?)" << '\n'; + out << R"(/// \brief Do arithmetics operations with \emph{float} check for underflow?)" << '\n'; out << "#define FLT_TINYNESS_BEFORE " << std::dec << std::numeric_limits::tinyness_before << '\n'; - out << R"(/// \brief Smallest positive, finite, normal value of \f$float\f$.)" << '\n'; + out << R"(/// \brief Smallest positive, finite, normal value of \emph{float}.)" << '\n'; out << "#define FLT_MIN " << "fennec::bit_cast(0x" << std::hex << std::bit_cast(std::numeric_limits::min() ) << ")" << '\n'; - out << R"(/// \brief Largest positive, finite value of \f$float\f$.)" << '\n'; + out << R"(/// \brief Largest positive, finite value of \emph{float}.)" << '\n'; out << "#define FLT_MAX " << "fennec::bit_cast(0x" << std::hex << std::bit_cast(std::numeric_limits::max() ) << ")" << '\n'; - out << R"(/// \brief The difference between \f$1.0\f$ and the next representable value of \f$float\f$.)" << '\n'; + out << R"(/// \brief The difference between \emph{1.0} and the next representable value of \emph{float}.)" << '\n'; out << "#define FLT_EPSILON " << "fennec::bit_cast(0x" << std::hex << std::bit_cast(std::numeric_limits::epsilon() ) << ")" << '\n'; - out << R"(/// \brief A value representing \f$\inf\f$ of type \f$float\f$.)" << '\n'; + out << R"(/// \brief A value representing \emph{\inf} of type \emph{float}.)" << '\n'; out << "#define FLT_INF " << "fennec::bit_cast(0x" << std::hex << std::bit_cast(std::numeric_limits::infinity() ) << ")" << '\n'; - out << R"(/// \brief A value representing \f$NaN\f$ of type \f$float\f$ that does not trap.)" << '\n'; + out << R"(/// \brief A value representing \emph{NaN} of type \emph{float} that does not trap.)" << '\n'; out << "#define FLT_QUIET_NAN " << "fennec::bit_cast(0x" << std::hex << std::bit_cast(std::numeric_limits::quiet_NaN() ) << ")" << '\n'; - out << R"(/// \brief A value representing \f$NaN\f$ of type \f$float\f$ that traps.)" << '\n'; + out << R"(/// \brief A value representing \emph{NaN} of type \emph{float} that traps.)" << '\n'; out << "#define FLT_SIGNALING_NAN " << "fennec::bit_cast(0x" << std::hex << std::bit_cast(std::numeric_limits::signaling_NaN()) << ")" << '\n'; - out << R"(/// \brief Smallest positive, finite, subnormal value of \f$float\f$.)" << '\n'; + out << R"(/// \brief Smallest positive, finite, subnormal value of \emph{float}.)" << '\n'; out << "#define FLT_DENORM_MIN " << "fennec::bit_cast(0x" << std::hex << std::bit_cast(std::numeric_limits::denorm_min() ) << ")" << '\n'; - out << R"(/// \brief Maximum rounding error of type \f$float\f$.)" << '\n'; + out << R"(/// \brief Maximum rounding error of type \emph{float}.)" << '\n'; out << "#define FLT_ROUND_ERR " << "fennec::bit_cast(0x" << std::hex << std::bit_cast(std::numeric_limits::round_error() ) << ")" << '\n'; out << "" << '\n'; @@ -209,80 +209,80 @@ inline void float_h() out << "" << '\n'; - out << R"(/// \brief Does \f$double\f$ have an infinity?)" << '\n'; + out << R"(/// \brief Does \emph{double} have an infinity?)" << '\n'; out << "#define DBL_HAS_INFINITY " << std::dec << std::numeric_limits::has_infinity << '\n'; - out << R"(/// \brief Does \f$double\f$ have a quiet NaN?)" << '\n'; + out << R"(/// \brief Does \emph{double} have a quiet NaN?)" << '\n'; out << "#define DBL_HAS_QUIET_NAN " << std::dec << std::numeric_limits::has_quiet_NaN << '\n'; - out << R"(/// \brief Does \f$double\f$ have a signaling NaN?)" << '\n'; + out << R"(/// \brief Does \emph{double} have a signaling NaN?)" << '\n'; out << "#define DBL_HAS_SIGNALING_NAN " << std::dec << std::numeric_limits::has_signaling_NaN << '\n'; - out << R"(/// \brief Does \f$double\f$ use denormalization?)" << '\n'; + out << R"(/// \brief Does \emph{double} use denormalization?)" << '\n'; out << "#define DBL_HAS_DENORM " << std::dec << std::numeric_limits::has_denorm << '\n'; - out << R"(/// \brief Does \f$double\f$ have loss with denormalization?)" << '\n'; + out << R"(/// \brief Does \emph{double} have loss with denormalization?)" << '\n'; out << "#define DBL_HAS_DENORM_LOSS " << std::dec << std::numeric_limits::has_denorm_loss << '\n'; - out << R"(/// \brief What rounding style does \f$double\f$ use?)" << '\n'; + out << R"(/// \brief What rounding style does \emph{double} use?)" << '\n'; out << "#define DBL_ROUNDS " << std::dec << std::numeric_limits::round_style << '\n'; - out << R"(/// \brief Does \f$double\f$ use the IEEE doubleing point specification?)" << '\n'; + out << R"(/// \brief Does \emph{double} use the IEEE doubleing point specification?)" << '\n'; out << "#define DBL_IS_IEC559 " << std::dec << std::numeric_limits::is_iec559 << '\n'; - out << R"(/// \brief The number of mantissa bits in \f$double\f$.)" << '\n'; + out << R"(/// \brief The number of mantissa bits in \emph{double}.)" << '\n'; out << "#define DBL_MANT_DIG " << std::dec << std::numeric_limits::digits << '\n'; - out << R"(/// \brief The number of decimal digits guaranteed to be preserved in a \f$double\f$ → \f$text\f$ → \f$double\f$.)" << '\n'; + out << R"(/// \brief The number of decimal digits guaranteed to be preserved in a \emph{double} → \emph{text} → \emph{double}.)" << '\n'; out << "#define DBL_DIG " << std::dec << std::numeric_limits::digits10 << '\n'; - out << R"(/// \brief The decimal precision required to serialize and deserialize a \f$double\f$.)" << '\n'; + out << R"(/// \brief The decimal precision required to serialize and deserialize a \emph{double}.)" << '\n'; out << "#define DBL_DECIMAL_DIG " << std::dec << std::numeric_limits::max_digits10 << '\n'; - out << R"(/// \brief The radix, or integer base, used to represent a \f$double\f$.)" << '\n'; + out << R"(/// \brief The radix, or integer base, used to represent a \emph{double}.)" << '\n'; out << "#define DBL_RADIX " << std::dec << std::numeric_limits::radix << '\n'; - out << R"(/// \brief The minimum negative integer such that \f${DBL_RADIX}^{DBL_MIN_EXP}\f$ results in a normalized \f$double\f$.)" << '\n'; + out << R"(/// \brief The minimum negative integer such that \math{\textbf{DBL_RADIX}^\textbf{DBL_MIN_EXP}} results in a normalized \emph{double}.)" << '\n'; out << "#define DBL_MIN_EXP " << std::dec << std::numeric_limits::min_exponent << '\n'; - out << R"(/// \brief The maximum positive integer such that \f${DBL_RADIX}^{DBL_MAX_EXP}\f$ results in a non-infinite \f$double\f$.)" << '\n'; + out << R"(/// \brief The maximum positive integer such that \math{\textbf{DBL_RADIX}^\textbf{DBL_MAX_EXP}} results in a non-infinite \emph{double}.)" << '\n'; out << "#define DBL_MAX_EXP " << std::dec << std::numeric_limits::max_exponent << '\n'; - out << R"(/// \brief The minimum negative integer such that \f${10}^{DBL_MIN_EXP}\f$ results in a normalized \f$double\f$.)" << '\n'; + out << R"(/// \brief The minimum negative integer such that \math{{10}^\textbf{DBL_MIN_EXP}} results in a normalized \emph{double}.)" << '\n'; out << "#define DBL_MIN_10_EXP " << std::dec << std::numeric_limits::min_exponent10 << '\n'; - out << R"(/// \brief The maximum positive integer such that \f${10}^{DBL_MAX_EXP}\f$ results in a non-infinite \f$double\f$.)" << '\n'; + out << R"(/// \brief The maximum positive integer such that \math{{10}^\textbf{DBL_MAX_EXP}} results in a non-infinite \emph{double}.)" << '\n'; out << "#define DBL_MAX_10_EXP " << std::dec << std::numeric_limits::max_exponent10 << '\n'; - out << R"(/// \brief Do arithmetics operations with \f$double\f$ trap?)" << '\n'; + out << R"(/// \brief Do arithmetics operations with \emph{double} trap?)" << '\n'; out << "#define DBL_TRAPS " << std::dec << std::numeric_limits::traps << '\n'; - out << R"(/// \brief Do arithmetics operations with \f$double\f$ check for underflow?)" << '\n'; + out << R"(/// \brief Do arithmetics operations with \emph{double} check for underflow?)" << '\n'; out << "#define DBL_TINYNESS_BEFORE " << std::dec << std::numeric_limits::tinyness_before << '\n'; - out << R"(/// \brief Smallest positive, finite, normal value of \f$double\f$.)" << '\n'; + out << R"(/// \brief Smallest positive, finite, normal value of \emph{double}.)" << '\n'; out << "#define DBL_MIN " << "fennec::bit_cast(0x" << std::hex << std::bit_cast(std::numeric_limits::min() ) << "ll)" << '\n'; - out << R"(/// \brief Largest positive, finite value of \f$double\f$.)" << '\n'; + out << R"(/// \brief Largest positive, finite value of \emph{double}.)" << '\n'; out << "#define DBL_MAX " << "fennec::bit_cast(0x" << std::hex << std::bit_cast(std::numeric_limits::max() ) << "ll)" << '\n'; - out << R"(/// \brief The difference between \f$1.0\f$ and the next representable value of \f$double\f$.)" << '\n'; + out << R"(/// \brief The difference between \emph{1.0} and the next representable value of \emph{double}.)" << '\n'; out << "#define DBL_EPSILON " << "fennec::bit_cast(0x" << std::hex << std::bit_cast(std::numeric_limits::epsilon() ) << "ll)" << '\n'; - out << R"(/// \brief A value representing \f$\inf\f$ of type \f$double\f$.)" << '\n'; + out << R"(/// \brief A value representing \emph{\inf} of type \emph{double}.)" << '\n'; out << "#define DBL_INF " << "fennec::bit_cast(0x" << std::hex << std::bit_cast(std::numeric_limits::infinity() ) << "ll)" << '\n'; - out << R"(/// \brief A value representing \f$NaN\f$ of type \f$double\f$ that does not trap.)" << '\n'; + out << R"(/// \brief A value representing \emph{NaN} of type \emph{double} that does not trap.)" << '\n'; out << "#define DBL_QUIET_NAN " << "fennec::bit_cast(0x" << std::hex << std::bit_cast(std::numeric_limits::quiet_NaN() ) << "ll)" << '\n'; - out << R"(/// \brief A value representing \f$NaN\f$ of type \f$double\f$ that traps.)" << '\n'; + out << R"(/// \brief A value representing \emph{NaN} of type \emph{double} that traps.)" << '\n'; out << "#define DBL_SIGNALING_NAN " << "fennec::bit_cast(0x" << std::hex << std::bit_cast(std::numeric_limits::signaling_NaN()) << "ll)" << '\n'; - out << R"(/// \brief Smallest positive, finite, subnormal value of \f$double\f$.)" << '\n'; + out << R"(/// \brief Smallest positive, finite, subnormal value of \emph{double}.)" << '\n'; out << "#define DBL_DENORM_MIN " << "fennec::bit_cast(0x" << std::hex << std::bit_cast(std::numeric_limits::denorm_min() ) << "ll)" << '\n'; - out << R"(/// \brief Maximum rounding error of type \f$double\f$.)" << '\n'; + out << R"(/// \brief Maximum rounding error of type \emph{double}.)" << '\n'; out << "#define DBL_ROUND_ERR " << "fennec::bit_cast(0x" << std::hex << std::bit_cast(std::numeric_limits::round_error() ) << "ll)" << '\n'; out << "" << '\n'; diff --git a/metaprogramming/integer.h b/metaprogramming/integer.h index cc807b1..3676e44 100644 --- a/metaprogramming/integer.h +++ b/metaprogramming/integer.h @@ -66,380 +66,388 @@ inline void integer_h() out << "" << '\n'; - out << "#undef CHAR_MIN" << '\n'; - out << "#undef CHAR_MAX" << '\n'; - out << "#undef WCHAR_MIN" << '\n'; - out << "#undef WCHAR_MAX" << '\n'; - out << "#undef SCHAR_MIN" << '\n'; - out << "#undef SCHAR_MAX" << '\n'; - out << "#undef UCHAR_MIN" << '\n'; - out << "#undef UCHAR_MAX" << '\n'; - out << "#undef INT_MIN" << '\n'; - out << "#undef INT_MAX" << '\n'; - out << "#undef UINT_MIN" << '\n'; - out << "#undef UINT_MAX" << '\n'; - out << "#undef LONG_MIN" << '\n'; - out << "#undef LONG_MAX" << '\n'; - out << "#undef ULONG_MIN" << '\n'; - out << "#undef ULONG_MAX" << '\n'; - out << "#undef LLONG_MIN" << '\n'; - out << "#undef LLONG_MAX" << '\n'; + out << "#undef CHAR_MIN" << '\n'; + out << "#undef CHAR_MAX" << '\n'; + out << "#undef WCHAR_MIN" << '\n'; + out << "#undef WCHAR_MAX" << '\n'; + out << "#undef SCHAR_MIN" << '\n'; + out << "#undef SCHAR_MAX" << '\n'; + out << "#undef UCHAR_MIN" << '\n'; + out << "#undef UCHAR_MAX" << '\n'; + out << "#undef INT_MIN" << '\n'; + out << "#undef INT_MAX" << '\n'; + out << "#undef UINT_MIN" << '\n'; + out << "#undef UINT_MAX" << '\n'; + out << "#undef LONG_MIN" << '\n'; + out << "#undef LONG_MAX" << '\n'; + out << "#undef ULONG_MIN" << '\n'; + out << "#undef ULONG_MAX" << '\n'; + out << "#undef LLONG_MIN" << '\n'; + out << "#undef LLONG_MAX" << '\n'; out << "#undef ULLONG_MIN" << '\n'; out << "#undef ULLONG_MAX" << '\n'; out << "" << '\n'; - // TODO: Fix this to generate info without using the c++stdlib for platforms without this available. + // TODO: Fix this to generate info without using the c+stdlib for platforms without this available. - out << R"(/// \brief Is \f$char\f$ signed?)" << '\n'; - out << "#define CHAR_IS_SIGNED " << std::boolalpha << std::numeric_limits::is_signed << '\n'; + out << R"(/// \brief Is \emph{char} signed?)" << '\n'; + out << "#define CHAR_IS_SIGNED " << std::boolalpha << std::numeric_limits::is_signed << '\n'; - out << R"(/// \brief Rounding style of type \f$char\f$.)" << '\n'; - out << "#define CHAR_ROUNDS " << "0x" << std::hex << (int)std::numeric_limits::round_style << '\n'; + out << R"(/// \brief Rounding style of type \emph{char}.)" << '\n'; + out << "#define CHAR_ROUNDS " << std::hex << std::showbase << (int)std::numeric_limits::round_style << '\n'; - out << R"(/// \brief Number of radix digits represented by \f$char\f$.)" << '\n'; - out << "#define CHAR_RADIX_DIG " << "0x" << std::hex << (int)std::numeric_limits::digits << '\n'; + out << R"(/// \brief Number of radix digits represented by \emph{char}.)" << '\n'; + out << "#define CHAR_RADIX_DIG " << std::hex << std::showbase << (int)std::numeric_limits::digits << '\n'; - out << R"(/// \brief Number of decimal digits represented by \f$char\f$.)" << '\n'; - out << "#define CHAR_DIG " << "0x" << std::hex << (int)std::numeric_limits::digits10 << '\n'; + out << R"(/// \brief Number of decimal digits represented by \emph{char}.)" << '\n'; + out << "#define CHAR_DIG " << std::hex << std::showbase << (int)std::numeric_limits::digits10 << '\n'; - out << R"(/// \brief Number of decimal digits necessary to differentiate all values of type \f$char\f$.)" << '\n'; - out << "#define CHAR_DECIMAL_DIG " << "0x" << std::hex << (int)std::numeric_limits::max_digits10 << '\n'; + out << R"(/// \brief Number of decimal digits necessary to differentiate all values of type \emph{char}.)" << '\n'; + out << "#define CHAR_DECIMAL_DIG " << std::hex << std::showbase << (int)std::numeric_limits::max_digits10 << '\n'; - out << R"(/// \brief The radix, or integer base, used to represent a \f$char\f$.)" << '\n'; - out << "#define CHAR_RADIX " << "0x" << std::hex << (int)std::numeric_limits::radix << '\n'; + out << R"(/// \brief The radix, or integer base, used to represent a \emph{char}.)" << '\n'; + out << "#define CHAR_RADIX " << std::hex << std::showbase << (int)std::numeric_limits::radix << '\n'; - out << R"(/// \brief Do arithmetics operations with \f$char\f$ trap?)" << '\n'; - out << "#define CHAR_TRAPS " << "0x" << std::boolalpha << std::numeric_limits::traps << '\n'; + out << R"(/// \brief Do arithmetics operations with \emph{char} trap?)" << '\n'; + out << "#define CHAR_TRAPS " << std::boolalpha << std::numeric_limits::traps << '\n'; - out << R"(/// \brief Smallest finite value of \f$char\f$.)" << '\n'; - out << "#define CHAR_MIN " << "0x" << std::hex << (0xFF & +std::numeric_limits::min()) << '\n'; + out << R"(/// \brief Smallest finite value of \emph{char}.)" << '\n'; + if (std::numeric_limits::is_signed) { + out << "#define CHAR_MIN -" << std::format("{:#2x}", 0xFF & std::numeric_limits::min()) << '\n'; + } else { + out << "#define CHAR_MIN " << std::format("{:#2x}", 0xFF & std::numeric_limits::min()) << '\n'; + } - out << R"(/// \brief Largest finite value of \f$char\f$.)" << '\n'; - out << "#define CHAR_MAX " << "0x" << std::hex << (0xFF & +std::numeric_limits::max()) << '\n'; + out << R"(/// \brief Largest finite value of \emph{char}.)" << '\n'; + out << "#define CHAR_MAX " << std::format("{:#2x}", 0xFF & std::numeric_limits::max()) << '\n'; out << "" << '\n'; - out << R"(/// \brief Is \f$wchar_t\f$ signed?)" << '\n'; - out << "#define WCHAR_IS_SIGNED " << std::boolalpha << std::numeric_limits::is_signed << '\n'; + out << R"(/// \brief Is \emph{wchar_t} signed?)" << '\n'; + out << "#define WCHAR_IS_SIGNED " << std::boolalpha << std::numeric_limits::is_signed << '\n'; - out << R"(/// \brief Rounding style of type \f$wchar_t\f$.)" << '\n'; - out << "#define WCHAR_ROUNDS " << "0x" << std::hex << std::numeric_limits::round_style << '\n'; + out << R"(/// \brief Rounding style of type \emph{wchar_t}.)" << '\n'; + out << "#define WCHAR_ROUNDS " << std::hex << std::showbase << std::numeric_limits::round_style << '\n'; - out << R"(/// \brief Number of radix digits represented by \f$wchar_t\f$.)" << '\n'; - out << "#define WCHAR_RADIX_DIG " << "0x" << std::hex << std::numeric_limits::digits << '\n'; + out << R"(/// \brief Number of radix digits represented by \emph{wchar_t}.)" << '\n'; + out << "#define WCHAR_RADIX_DIG " << std::hex << std::showbase << std::numeric_limits::digits << '\n'; - out << R"(/// \brief Number of decimal digits represented by \f$wchar_t\f$.)" << '\n'; - out << "#define WCHAR_DIG " << "0x" << std::hex << std::numeric_limits::digits10 << '\n'; + out << R"(/// \brief Number of decimal digits represented by \emph{wchar_t}.)" << '\n'; + out << "#define WCHAR_DIG " << std::hex << std::showbase << std::numeric_limits::digits10 << '\n'; - out << R"(/// \brief Number of decimal digits necessary to differentiate all values of type \f$wchar_t\f$.)" << '\n'; - out << "#define WCHAR_DECIMAL_DIG " << "0x" << std::hex << std::numeric_limits::max_digits10 << '\n'; + out << R"(/// \brief Number of decimal digits necessary to differentiate all values of type \emph{wchar_t}.)" << '\n'; + out << "#define WCHAR_DECIMAL_DIG " << std::hex << std::showbase << std::numeric_limits::max_digits10 << '\n'; - out << R"(/// \brief The radix, or integer base, used to represent a \f$wchar_t\f$.)" << '\n'; - out << "#define WCHAR_RADIX " << "0x" << std::hex << std::numeric_limits::radix << '\n'; + out << R"(/// \brief The radix, or integer base, used to represent a \emph{wchar_t}.)" << '\n'; + out << "#define WCHAR_RADIX " << std::hex << std::showbase << std::numeric_limits::radix << '\n'; - out << R"(/// \brief Do arithmetics operations with \f$wchar_t\f$ trap?)" << '\n'; - out << "#define WCHAR_TRAPS " << "0x" << std::boolalpha << std::numeric_limits::traps << '\n'; + out << R"(/// \brief Do arithmetics operations with \emph{wchar_t} trap?)" << '\n'; + out << "#define WCHAR_TRAPS " << std::boolalpha << std::numeric_limits::traps << '\n'; - out << R"(/// \brief Smallest finite value of \f$wchar_t\f$.)" << '\n'; - out << "#define WCHAR_MIN " << "0x" << std::hex << +std::numeric_limits::min() << '\n'; + out << R"(/// \brief Smallest finite value of \emph{wchar_t}.)" << '\n'; + if (std::numeric_limits::is_signed) { + out << "#define WCHAR_MIN -" << std::format("{:#4x}", 0xFFFF & std::numeric_limits::min()) << '\n'; + } else { + out << "#define WCHAR_MIN " << std::format("{:#4x}", 0xFFFF & std::numeric_limits::min()) << '\n'; + } - out << R"(/// \brief Largest finite value of \f$wchar_t\f$.)" << '\n'; - out << "#define WCHAR_MAX " << "0x" << std::hex << +std::numeric_limits::max() << '\n'; + out << R"(/// \brief Largest finite value of \emph{wchar_t}.)" << '\n'; + out << "#define WCHAR_MAX " << std::format("{:#04x}", 0xFFFF & std::numeric_limits::max()) << '\n'; out << "" << '\n'; - out << R"(/// \brief Is \f$signed char\f$ signed?)" << '\n'; - out << "#define SCHAR_ROUNDS " << "0x" << std::hex << (int)std::numeric_limits::round_style << '\n'; + out << R"(/// \brief Rounding style of type \emph{signed char}.)" << '\n'; + out << "#define SCHAR_ROUNDS " << std::hex << std::showbase << (int)std::numeric_limits::round_style << '\n'; - out << R"(/// \brief Rounding style of type \f$signed char\f$.)" << '\n'; - out << "#define SCHAR_RADIX_DIG " << "0x" << std::hex << (int)std::numeric_limits::digits << '\n'; + out << R"(/// \brief Number of radix digits represented by \emph{signed char}.)" << '\n'; + out << "#define SCHAR_RADIX_DIG " << std::hex << std::showbase << (int)std::numeric_limits::digits << '\n'; - out << R"(/// \brief Number of radix digits represented by \f$signed char\f$.)" << '\n'; - out << "#define SCHAR_DIG " << "0x" << std::hex << (int)std::numeric_limits::digits10 << '\n'; + out << R"(/// \brief Number of decimal digits represented by \emph{signed char}.)" << '\n'; + out << "#define SCHAR_DIG " << std::hex << std::showbase << (int)std::numeric_limits::digits10 << '\n'; - out << R"(/// \brief Number of decimal digits represented by \f$signed char\f$.)" << '\n'; - out << "#define SCHAR_DECIMAL_DIG " << "0x" << std::hex << (int)std::numeric_limits::max_digits10 << '\n'; + out << R"(/// \brief Number of decimal digits necessary to differentiate all values of type \emph{signed char}.)" << '\n'; + out << "#define SCHAR_DECIMAL_DIG " << std::hex << std::showbase << (int)std::numeric_limits::max_digits10 << '\n'; - out << R"(/// \brief Number of decimal digits necessary to differentiate all values of type \f$signed char\f$.)" << '\n'; - out << "#define SCHAR_RADIX " << "0x" << std::hex << (int)std::numeric_limits::radix << '\n'; + out << R"(/// \brief The radix, or integer base, used to represent a \emph{signed char}.)" << '\n'; + out << "#define SCHAR_RADIX " << std::hex << std::showbase << (int)std::numeric_limits::radix << '\n'; - out << R"(/// \brief Do arithmetics operations with \f$signed char\f$ trap?)" << '\n'; - out << "#define SCHAR_TRAPS " << "0x" << std::boolalpha << std::numeric_limits::traps << '\n'; + out << R"(/// \brief Do arithmetics operations with \emph{signed char} trap?)" << '\n'; + out << "#define SCHAR_TRAPS " << std::boolalpha << std::numeric_limits::traps << '\n'; - out << R"(/// \brief Smallest finite value of \f$signed char\f$.)" << '\n'; - out << "#define SCHAR_MIN " << "0x" << std::hex << (0xFF & +std::numeric_limits::min()) << '\n'; + out << R"(/// \brief Smallest finite value of \emph{signed char}.)" << '\n'; + out << "#define SCHAR_MIN -" << std::format("{:#2x}", 0xFF & std::numeric_limits::min()) << '\n'; - out << R"(/// \brief Largest finite value of \f$signed char\f$.)" << '\n'; - out << "#define SCHAR_MAX " << "0x" << std::hex << (0xFF & +std::numeric_limits::max()) << '\n'; + out << R"(/// \brief Largest finite value of \emph{signed char}.)" << '\n'; + out << "#define SCHAR_MAX " << std::format("{:#2x}", 0xFF & std::numeric_limits::max()) << '\n'; out << "" << '\n'; - out << R"(/// \brief Is \f$unsigned char\f$ unsigned?)" << '\n'; - out << "#define UCHAR_ROUNDS " << "0x" << std::hex << (int)std::numeric_limits::round_style << '\n'; + out << R"(/// \brief Rounding style of type \emph{unsigned char}.)" << '\n'; + out << "#define UCHAR_ROUNDS " << std::hex << std::showbase << (int)std::numeric_limits::round_style << '\n'; - out << R"(/// \brief Rounding style of type \f$unsigned char\f$.)" << '\n'; - out << "#define UCHAR_RADIX_DIG " << "0x" << std::hex << (int)std::numeric_limits::digits << '\n'; + out << R"(/// \brief Number of radix digits represented by \emph{unsigned char}.)" << '\n'; + out << "#define UCHAR_RADIX_DIG " << std::hex << std::showbase << (int)std::numeric_limits::digits << '\n'; - out << R"(/// \brief Number of radix digits represented by \f$unsigned char\f$.)" << '\n'; - out << "#define UCHAR_DIG " << "0x" << std::hex << (int)std::numeric_limits::digits10 << '\n'; + out << R"(/// \brief Number of decimal digits represented by \emph{unsigned char}.)" << '\n'; + out << "#define UCHAR_DIG " << std::hex << std::showbase << (int)std::numeric_limits::digits10 << '\n'; - out << R"(/// \brief Number of decimal digits represented by \f$unsigned char\f$.)" << '\n'; - out << "#define UCHAR_DECIMAL_DIG " << "0x" << std::hex << (int)std::numeric_limits::max_digits10 << '\n'; + out << R"(/// \brief Number of decimal digits necessary to differentiate all values of type \emph{unsigned char}.)" << '\n'; + out << "#define UCHAR_DECIMAL_DIG " << std::hex << std::showbase << (int)std::numeric_limits::max_digits10 << '\n'; - out << R"(/// \brief Number of decimal digits necessary to differentiate all values of type \f$unsigned char\f$.)" << '\n'; - out << "#define UCHAR_RADIX " << "0x" << std::hex << (int)std::numeric_limits::radix << '\n'; + out << R"(/// \brief The radix, or integer base, used to represent an \emph{unsigned char}.)" << '\n'; + out << "#define UCHAR_RADIX " << std::hex << std::showbase << (int)std::numeric_limits::radix << '\n'; - out << R"(/// \brief Do arithmetics operations with \f$unsigned char\f$ trap?)" << '\n'; - out << "#define UCHAR_TRAPS " << "0x" << std::boolalpha << std::numeric_limits::traps << '\n'; + out << R"(/// \brief Do arithmetics operations with \emph{unsigned char} trap?)" << '\n'; + out << "#define UCHAR_TRAPS " << std::boolalpha << std::numeric_limits::traps << '\n'; - out << R"(/// \brief Smallest finite value of \f$unsigned char\f$.)" << '\n'; - out << "#define UCHAR_MIN " << "0x" << std::hex << (0xFF & +std::numeric_limits::min()) << '\n'; + out << R"(/// \brief Smallest finite value of \emph{unsigned char}.)" << '\n'; + out << "#define UCHAR_MIN " << std::format("{:#2x}", 0xFF & std::numeric_limits::min()) << '\n'; - out << R"(/// \brief Largest finite value of \f$unsigned char\f$.)" << '\n'; - out << "#define UCHAR_MAX " << "0x" << std::hex << (0xFF & +std::numeric_limits::max()) << '\n'; + out << R"(/// \brief Largest finite value of \emph{unsigned char}.)" << '\n'; + out << "#define UCHAR_MAX " << std::format("{:#2x}", 0xFF & std::numeric_limits::max()) << '\n'; out << "" << '\n'; - out << R"(/// \brief Rounding style of type \f$short\f$.)" << '\n'; - out << "#define SHORT_ROUNDS " << "0x" << std::hex << std::numeric_limits::round_style << '\n'; + out << R"(/// \brief Rounding style of type \emph{short}.)" << '\n'; + out << "#define SHORT_ROUNDS " << std::hex << std::showbase << std::numeric_limits::round_style << '\n'; - out << R"(/// \brief Number of radix digits represented by \f$short\f$.)" << '\n'; - out << "#define SHORT_RADIX_DIG " << "0x" << std::hex << std::numeric_limits::digits << '\n'; + out << R"(/// \brief Number of radix digits represented by \emph{short}.)" << '\n'; + out << "#define SHORT_RADIX_DIG " << std::hex << std::showbase << std::numeric_limits::digits << '\n'; - out << R"(/// \brief Number of decimal digits represented by \f$short\f$.)" << '\n'; - out << "#define SHORT_DIG " << "0x" << std::hex << std::numeric_limits::digits10 << '\n'; + out << R"(/// \brief Number of decimal digits represented by \emph{short}.)" << '\n'; + out << "#define SHORT_DIG " << std::hex << std::showbase << std::numeric_limits::digits10 << '\n'; - out << R"(/// \brief Number of decimal digits necessary to differentiate all values of type \f$short\f$.)" << '\n'; - out << "#define SHORT_DECIMAL_DIG " << "0x" << std::hex << std::numeric_limits::max_digits10 << '\n'; + out << R"(/// \brief Number of decimal digits necessary to differentiate all values of type \emph{short}.)" << '\n'; + out << "#define SHORT_DECIMAL_DIG " << std::hex << std::showbase << std::numeric_limits::max_digits10 << '\n'; - out << R"(/// \brief The radix, or integer base, used to represent a \f$short\f$.)" << '\n'; - out << "#define SHORT_RADIX " << "0x" << std::hex << std::numeric_limits::radix << '\n'; + out << R"(/// \brief The radix, or integer base, used to represent a \emph{short}.)" << '\n'; + out << "#define SHORT_RADIX " << std::hex << std::showbase << std::numeric_limits::radix << '\n'; - out << R"(/// \brief Do arithmetics operations with \f$short\f$ trap?)" << '\n'; - out << "#define SHORT_TRAPS " << "0x" << std::boolalpha << std::numeric_limits::traps << '\n'; + out << R"(/// \brief Do arithmetics operations with \emph{short} trap?)" << '\n'; + out << "#define SHORT_TRAPS " << std::boolalpha << std::numeric_limits::traps << '\n'; - out << R"(/// \brief Smallest finite value of \f$short\f$.)" << '\n'; - out << "#define SHORT_MIN " << "0x" << std::hex << +std::numeric_limits::min() << '\n'; + out << R"(/// \brief Smallest finite value of \emph{short}.)" << '\n'; + out << "#define SHORT_MIN " << std::hex << std::showbase << std::numeric_limits::min() << '\n'; - out << R"(/// \brief Largest finite value of \f$short\f$.)" << '\n'; - out << "#define SHORT_MAX " << "0x" << std::hex << +std::numeric_limits::max() << '\n'; + out << R"(/// \brief Largest finite value of \emph{short}.)" << '\n'; + out << "#define SHORT_MAX " << std::hex << std::showbase << std::numeric_limits::max() << '\n'; out << "" << '\n'; - out << R"(/// \brief Rounding style of type \f$unsigned short\f$.)" << '\n'; - out << "#define USHORT_ROUNDS " << "0x" << std::hex << std::numeric_limits::round_style << '\n'; + out << R"(/// \brief Rounding style of type \emph{unsigned short}.)" << '\n'; + out << "#define USHORT_ROUNDS " << std::hex << std::showbase << std::numeric_limits::round_style << '\n'; - out << R"(/// \brief Number of radix digits represented by \f$unsigned short\f$.)" << '\n'; - out << "#define USHORT_RADIX_DIG " << "0x" << std::hex << std::numeric_limits::digits << '\n'; + out << R"(/// \brief Number of radix digits represented by \emph{unsigned short}.)" << '\n'; + out << "#define USHORT_RADIX_DIG " << std::hex << std::showbase << std::numeric_limits::digits << '\n'; - out << R"(/// \brief Number of decimal digits represented by \f$unsigned short\f$.)" << '\n'; - out << "#define USHORT_DIG " << "0x" << std::hex << std::numeric_limits::digits10 << '\n'; + out << R"(/// \brief Number of decimal digits represented by \emph{unsigned short}.)" << '\n'; + out << "#define USHORT_DIG " << std::hex << std::showbase << std::numeric_limits::digits10 << '\n'; - out << R"(/// \brief Number of decimal digits necessary to differentiate all values of type \f$unsigned short\f$.)" << '\n'; - out << "#define USHORT_DECIMAL_DIG " << "0x" << std::hex << std::numeric_limits::max_digits10 << '\n'; + out << R"(/// \brief Number of decimal digits necessary to differentiate all values of type \emph{unsigned short}.)" << '\n'; + out << "#define USHORT_DECIMAL_DIG " << std::hex << std::showbase << std::numeric_limits::max_digits10 << '\n'; - out << R"(/// \brief The radix, or integer base, used to represent a \f$unsigned short\f$.)" << '\n'; - out << "#define USHORT_RADIX " << "0x" << std::hex << std::numeric_limits::radix << '\n'; + out << R"(/// \brief The radix, or integer base, used to represent an \emph{unsigned short}.)" << '\n'; + out << "#define USHORT_RADIX " << std::hex << std::showbase << std::numeric_limits::radix << '\n'; - out << R"(/// \brief Do arithmetics operations with \f$unsigned short\f$ trap?)" << '\n'; - out << "#define USHORT_TRAPS " << "0x" << std::boolalpha << std::numeric_limits::traps << '\n'; + out << R"(/// \brief Do arithmetics operations with \emph{unsigned short} trap?)" << '\n'; + out << "#define USHORT_TRAPS " << std::boolalpha << std::numeric_limits::traps << '\n'; - out << R"(/// \brief Smallest finite value of \f$unsigned short\f$.)" << '\n'; - out << "#define USHORT_MIN " << "0x" << std::hex << +std::numeric_limits::min() << '\n'; + out << R"(/// \brief Smallest finite value of \emph{unsigned short}.)" << '\n'; + out << "#define USHORT_MIN " << std::hex << std::showbase << std::numeric_limits::min() << '\n'; + + out << R"(/// \brief Largest finite value of \emph{unsigned short}.)" << '\n'; + out << "#define USHORT_MAX " << std::hex << std::showbase << std::numeric_limits::max() << '\n'; - out << R"(/// \brief Largest finite value of \f$unsigned short\f$.)" << '\n'; - out << "#define USHORT_MAX " << "0x" << std::hex << +std::numeric_limits::max() << '\n'; - out << "" << '\n'; - out << R"(/// \brief Rounding style of type \f$int\f$.)" << '\n'; - out << "#define INT_ROUNDS " << "0x" << std::hex << std::numeric_limits::round_style << '\n'; + out << R"(/// \brief Rounding style of type \emph{int}.)" << '\n'; + out << "#define INT_ROUNDS " << std::hex << std::showbase << std::numeric_limits::round_style << '\n'; - out << R"(/// \brief Number of radix digits represented by \f$int\f$.)" << '\n'; - out << "#define INT_RADIX_DIG " << "0x" << std::hex << std::numeric_limits::digits << '\n'; + out << R"(/// \brief Number of radix digits represented by \emph{int}.)" << '\n'; + out << "#define INT_RADIX_DIG " << std::hex << std::showbase << std::numeric_limits::digits << '\n'; - out << R"(/// \brief Number of decimal digits represented by \f$int\f$.)" << '\n'; - out << "#define INT_DIG " << "0x" << std::hex << std::numeric_limits::digits10 << '\n'; + out << R"(/// \brief Number of decimal digits represented by \emph{int}.)" << '\n'; + out << "#define INT_DIG " << std::hex << std::showbase << std::numeric_limits::digits10 << '\n'; - out << R"(/// \brief Number of decimal digits necessary to differentiate all values of type \f$int\f$.)" << '\n'; - out << "#define INT_DECIMAL_DIG " << "0x" << std::hex << std::numeric_limits::max_digits10 << '\n'; + out << R"(/// \brief Number of decimal digits necessary to differentiate all values of type \emph{int}.)" << '\n'; + out << "#define INT_DECIMAL_DIG " << std::hex << std::showbase << std::numeric_limits::max_digits10 << '\n'; - out << R"(/// \brief The radix, or integer base, used to represent a \f$int\f$.)" << '\n'; - out << "#define INT_RADIX " << "0x" << std::hex << std::numeric_limits::radix << '\n'; + out << R"(/// \brief The radix, or integer base, used to represent an \emph{int}.)" << '\n'; + out << "#define INT_RADIX " << std::hex << std::showbase << std::numeric_limits::radix << '\n'; - out << R"(/// \brief Do arithmetics operations with \f$int\f$ trap?)" << '\n'; - out << "#define INT_TRAPS " << "0x" << std::boolalpha << std::numeric_limits::traps << '\n'; + out << R"(/// \brief Do arithmetics operations with \emph{int} trap?)" << '\n'; + out << "#define INT_TRAPS " << std::boolalpha << std::numeric_limits::traps << '\n'; - out << R"(/// \brief Smallest finite value of \f$int\f$.)" << '\n'; - out << "#define INT_MIN " << "0x" << std::hex << +std::numeric_limits::min() << '\n'; + out << R"(/// \brief Smallest finite value of \emph{int}.)" << '\n'; + out << "#define INT_MIN " << std::hex << std::showbase << std::numeric_limits::min() << '\n'; + + out << R"(/// \brief Largest finite value of \emph{int}.)" << '\n'; + out << "#define INT_MAX " << std::hex << std::showbase << std::numeric_limits::max() << '\n'; - out << R"(/// \brief Largest finite value of \f$int\f$.)" << '\n'; - out << "#define INT_MAX " << "0x" << std::hex << +std::numeric_limits::max() << '\n'; - out << "" << '\n'; - out << R"(/// \brief Rounding style of type \f$unsigned int\f$.)" << '\n'; - out << "#define UINT_ROUNDS " << "0x" << std::hex << std::numeric_limits::round_style << '\n'; + out << R"(/// \brief Rounding style of type \emph{unsigned int}.)" << '\n'; + out << "#define UINT_ROUNDS " << std::hex << std::showbase << std::numeric_limits::round_style << '\n'; - out << R"(/// \brief Number of radix digits represented by \f$unsigned int\f$.)" << '\n'; - out << "#define UINT_RADIX_DIG " << "0x" << std::hex << std::numeric_limits::digits << '\n'; + out << R"(/// \brief Number of radix digits represented by \emph{unsigned int}.)" << '\n'; + out << "#define UINT_RADIX_DIG " << std::hex << std::showbase << std::numeric_limits::digits << '\n'; - out << R"(/// \brief Number of decimal digits represented by \f$unsigned int\f$.)" << '\n'; - out << "#define UINT_DIG " << "0x" << std::hex << std::numeric_limits::digits10 << '\n'; + out << R"(/// \brief Number of decimal digits represented by \emph{unsigned int}.)" << '\n'; + out << "#define UINT_DIG " << std::hex << std::showbase << std::numeric_limits::digits10 << '\n'; - out << R"(/// \brief Number of decimal digits necessary to differentiate all values of type \f$unsigned int\f$.)" << '\n'; - out << "#define UINT_DECIMAL_DIG " << "0x" << std::hex << std::numeric_limits::max_digits10 << '\n'; + out << R"(/// \brief Number of decimal digits necessary to differentiate all values of type \emph{unsigned int}.)" << '\n'; + out << "#define UINT_DECIMAL_DIG " << std::hex << std::showbase << std::numeric_limits::max_digits10 << '\n'; - out << R"(/// \brief The radix, or unsigned integer base, used to represent a \f$unsigned int\f$.)" << '\n'; - out << "#define UINT_RADIX " << "0x" << std::hex << std::numeric_limits::radix << '\n'; + out << R"(/// \brief The radix, or integer base, used to represent an \emph{unsigned int}.)" << '\n'; + out << "#define UINT_RADIX " << std::hex << std::showbase << std::numeric_limits::radix << '\n'; - out << R"(/// \brief Do arithmetics operations with \f$unsigned int\f$ trap?)" << '\n'; - out << "#define UINT_TRAPS " << "0x" << std::boolalpha << std::numeric_limits::traps << '\n'; + out << R"(/// \brief Do arithmetics operations with \emph{unsigned int} trap?)" << '\n'; + out << "#define UINT_TRAPS " << std::boolalpha << std::numeric_limits::traps << '\n'; - out << R"(/// \brief Smallest finite value of \f$unsigned int\f$.)" << '\n'; - out << "#define UINT_MIN " << "0x" << std::hex << +std::numeric_limits::min() << '\n'; + out << R"(/// \brief Smallest finite value of \emph{unsigned int}.)" << '\n'; + out << "#define UINT_MIN " << std::hex << std::showbase << std::numeric_limits::min() << '\n'; + + out << R"(/// \brief Largest finite value of \emph{unsigned int}.)" << '\n'; + out << "#define UINT_MAX " << std::hex << std::showbase << std::numeric_limits::max() << '\n'; - out << R"(/// \brief Largest finite value of \f$unsigned int\f$.)" << '\n'; - out << "#define UINT_MAX " << "0x" << std::hex << +std::numeric_limits::max() << '\n'; - out << "" << '\n'; - out << R"(/// \brief Rounding style of type \f$long int\f$.)" << '\n'; - out << "#define LONG_ROUNDS " << "0x" << std::hex << std::numeric_limits::round_style << '\n'; + out << R"(/// \brief Rounding style of type \emph{long int}.)" << '\n'; + out << "#define LONG_ROUNDS " << std::hex << std::showbase << std::numeric_limits::round_style << '\n'; - out << R"(/// \brief Number of radix digits represented by \f$long int\f$.)" << '\n'; - out << "#define LONG_RADIX_DIG " << "0x" << std::hex << std::numeric_limits::digits << '\n'; + out << R"(/// \brief Number of radix digits represented by \emph{long int}.)" << '\n'; + out << "#define LONG_RADIX_DIG " << std::hex << std::showbase << std::numeric_limits::digits << '\n'; - out << R"(/// \brief Number of decimal digits represented by \f$long int\f$.)" << '\n'; - out << "#define LONG_DIG " << "0x" << std::hex << std::numeric_limits::digits10 << '\n'; + out << R"(/// \brief Number of decimal digits represented by \emph{long int}.)" << '\n'; + out << "#define LONG_DIG " << std::hex << std::showbase << std::numeric_limits::digits10 << '\n'; - out << R"(/// \brief Number of decimal digits necessary to differentiate all values of type \f$long int\f$.)" << '\n'; - out << "#define LONG_DECIMAL_DIG " << "0x" << std::hex << std::numeric_limits::max_digits10 << '\n'; + out << R"(/// \brief Number of decimal digits necessary to differentiate all values of type \emph{long int}.)" << '\n'; + out << "#define LONG_DECIMAL_DIG " << std::hex << std::showbase << std::numeric_limits::max_digits10 << '\n'; - out << R"(/// \brief The radix, or long integer base, used to represent a \f$long int\f$.)" << '\n'; - out << "#define LONG_RADIX " << "0x" << std::hex << std::numeric_limits::radix << '\n'; + out << R"(/// \brief The radix, or integer base, used to represent a \emph{long int}.)" << '\n'; + out << "#define LONG_RADIX " << std::hex << std::showbase << std::numeric_limits::radix << '\n'; - out << R"(/// \brief Do arithmetics operations with \f$long int\f$ trap?)" << '\n'; - out << "#define LONG_TRAPS " << "0x" << std::boolalpha << std::numeric_limits::traps << '\n'; + out << R"(/// \brief Do arithmetics operations with \emph{long int} trap?)" << '\n'; + out << "#define LONG_TRAPS " << std::boolalpha << std::numeric_limits::traps << '\n'; - out << R"(/// \brief Smallest finite value of \f$long int\f$.)" << '\n'; - out << "#define LONG_MIN " << "0x" << std::hex << +std::numeric_limits::min() << '\n'; + out << R"(/// \brief Smallest finite value of \emph{long int}.)" << '\n'; + out << "#define LONG_MIN " << std::hex << std::showbase << std::numeric_limits::min() << '\n'; + + out << R"(/// \brief Largest finite value of \emph{long int}.)" << '\n'; + out << "#define LONG_MAX " << std::hex << std::showbase << std::numeric_limits::max() << '\n'; - out << R"(/// \brief Largest finite value of \f$long int\f$.)" << '\n'; - out << "#define LONG_MAX " << "0x" << std::hex << +std::numeric_limits::max() << '\n'; - out << "" << '\n'; - out << R"(/// \brief Rounding style of type \f$unsigned long int\f$.)" << '\n'; - out << "#define ULONG_ROUNDS " << "0x" << std::hex << std::numeric_limits::round_style << '\n'; + out << R"(/// \brief Rounding style of type \emph{unsigned long int}.)" << '\n'; + out << "#define ULONG_ROUNDS " << std::hex << std::showbase << std::numeric_limits::round_style << '\n'; - out << R"(/// \brief Number of radix digits represented by \f$unsigned long int\f$.)" << '\n'; - out << "#define ULONG_RADIX_DIG " << "0x" << std::hex << std::numeric_limits::digits << '\n'; + out << R"(/// \brief Number of radix digits represented by \emph{unsigned long int}.)" << '\n'; + out << "#define ULONG_RADIX_DIG " << std::hex << std::showbase << std::numeric_limits::digits << '\n'; - out << R"(/// \brief Number of decimal digits represented by \f$unsigned long int\f$.)" << '\n'; - out << "#define ULONG_DIG " << "0x" << std::hex << std::numeric_limits::digits10 << '\n'; + out << R"(/// \brief Number of decimal digits represented by \emph{unsigned long int}.)" << '\n'; + out << "#define ULONG_DIG " << std::hex << std::showbase << std::numeric_limits::digits10 << '\n'; - out << R"(/// \brief Number of decimal digits necessary to differentiate all values of type \f$unsigned long int\f$.)" << '\n'; - out << "#define ULONG_DECIMAL_DIG " << "0x" << std::hex << std::numeric_limits::max_digits10 << '\n'; + out << R"(/// \brief Number of decimal digits necessary to differentiate all values of type \emph{unsigned long int}.)" << '\n'; + out << "#define ULONG_DECIMAL_DIG " << std::hex << std::showbase << std::numeric_limits::max_digits10 << '\n'; - out << R"(/// \brief The radix, or unsigned long integer base, used to represent a \f$unsigned long int\f$.)" << '\n'; - out << "#define ULONG_RADIX " << "0x" << std::hex << std::numeric_limits::radix << '\n'; + out << R"(/// \brief The radix, or integer base, used to represent an \emph{unsigned long int}.)" << '\n'; + out << "#define ULONG_RADIX " << std::hex << std::showbase << std::numeric_limits::radix << '\n'; - out << R"(/// \brief Do arithmetics operations with \f$unsigned long int\f$ trap?)" << '\n'; - out << "#define ULONG_TRAPS " << "0x" << std::boolalpha << std::numeric_limits::traps << '\n'; + out << R"(/// \brief Do arithmetics operations with \emph{unsigned long int} trap?)" << '\n'; + out << "#define ULONG_TRAPS " << std::boolalpha << std::numeric_limits::traps << '\n'; - out << R"(/// \brief Smallest finite value of \f$unsigned long int\f$.)" << '\n'; - out << "#define ULONG_MIN " << "0x" << std::hex << +std::numeric_limits::min() << '\n'; + out << R"(/// \brief Smallest finite value of \emph{unsigned long int}.)" << '\n'; + out << "#define ULONG_MIN " << std::hex << std::showbase << std::numeric_limits::min() << '\n'; + + out << R"(/// \brief Largest finite value of \emph{unsigned long int}.)" << '\n'; + out << "#define ULONG_MAX " << std::hex << std::showbase << std::numeric_limits::max() << '\n'; - out << R"(/// \brief Largest finite value of \f$unsigned long int\f$.)" << '\n'; - out << "#define ULONG_MAX " << "0x" << std::hex << +std::numeric_limits::max() << '\n'; - out << "" << '\n'; - out << R"(/// \brief Rounding style of type \f$long long\f$.)" << '\n'; - out << "#define LLONG_ROUNDS " << "0x" << std::hex << std::numeric_limits::round_style << '\n'; + out << R"(/// \brief Rounding style of type \emph{long long}.)" << '\n'; + out << "#define LLONG_ROUNDS " << std::hex << std::showbase << std::numeric_limits::round_style << '\n'; - out << R"(/// \brief Number of radix digits represented by \f$long long\f$.)" << '\n'; - out << "#define LLONG_RADIX_DIG " << "0x" << std::hex << std::numeric_limits::digits << '\n'; + out << R"(/// \brief Number of radix digits represented by \emph{long long}.)" << '\n'; + out << "#define LLONG_RADIX_DIG " << std::hex << std::showbase << std::numeric_limits::digits << '\n'; - out << R"(/// \brief Number of decimal digits represented by \f$long long\f$.)" << '\n'; - out << "#define LLONG_DIG " << "0x" << std::hex << std::numeric_limits::digits10 << '\n'; + out << R"(/// \brief Number of decimal digits represented by \emph{long long}.)" << '\n'; + out << "#define LLONG_DIG " << std::hex << std::showbase << std::numeric_limits::digits10 << '\n'; - out << R"(/// \brief Number of decimal digits necessary to differentiate all values of type \f$long long\f$.)" << '\n'; - out << "#define LLONG_DECIMAL_DIG " << "0x" << std::hex << std::numeric_limits::max_digits10 << '\n'; + out << R"(/// \brief Number of decimal digits necessary to differentiate all values of type \emph{long long}.)" << '\n'; + out << "#define LLONG_DECIMAL_DIG " << std::hex << std::showbase << std::numeric_limits::max_digits10 << '\n'; - out << R"(/// \brief The radix, or long longeger base, used to represent a \f$long long\f$.)" << '\n'; - out << "#define LLONG_RADIX " << "0x" << std::hex << std::numeric_limits::radix << '\n'; + out << R"(/// \brief The radix, or integer base, used to represent a \emph{long long}.)" << '\n'; + out << "#define LLONG_RADIX " << std::hex << std::showbase << std::numeric_limits::radix << '\n'; - out << R"(/// \brief Do arithmetics operations with \f$long long\f$ trap?)" << '\n'; - out << "#define LLONG_TRAPS " << "0x" << std::boolalpha << std::numeric_limits::traps << '\n'; + out << R"(/// \brief Do arithmetics operations with \emph{long long} trap?)" << '\n'; + out << "#define LLONG_TRAPS " << std::boolalpha << std::numeric_limits::traps << '\n'; - out << R"(/// \brief Smallest finite value of \f$long long\f$.)" << '\n'; - out << "#define LLONG_MIN " << "0x" << std::hex << +std::numeric_limits::min() << '\n'; + out << R"(/// \brief Smallest finite value of \emph{long long}.)" << '\n'; + out << "#define LLONG_MIN " << std::hex << std::showbase << std::numeric_limits::min() << '\n'; + + out << R"(/// \brief Largest finite value of \emph{long long}.)" << '\n'; + out << "#define LLONG_MAX " << std::hex << std::showbase << std::numeric_limits::max() << '\n'; - out << R"(/// \brief Largest finite value of \f$long long\f$.)" << '\n'; - out << "#define LLONG_MAX " << "0x" << std::hex << +std::numeric_limits::max() << '\n'; - out << "" << '\n'; - out << R"(/// \brief Rounding style of type \f$unsigned long long\f$.)" << '\n'; - out << "#define ULLONG_ROUNDS " << "0x" << std::hex << std::numeric_limits::round_style << '\n'; + out << R"(/// \brief Rounding style of type \emph{unsigned long long}.)" << '\n'; + out << "#define ULLONG_ROUNDS " << std::hex << std::showbase << std::numeric_limits::round_style << '\n'; - out << R"(/// \brief Number of radix digits represented by \f$unsigned long long\f$.)" << '\n'; - out << "#define ULLONG_RADIX_DIG " << "0x" << std::hex << std::numeric_limits::digits << '\n'; + out << R"(/// \brief Number of radix digits represented by \emph{unsigned long long}.)" << '\n'; + out << "#define ULLONG_RADIX_DIG " << std::hex << std::showbase << std::numeric_limits::digits << '\n'; - out << R"(/// \brief Number of decimal digits represented by \f$unsigned long long\f$.)" << '\n'; - out << "#define ULLONG_DIG " << "0x" << std::hex << std::numeric_limits::digits10 << '\n'; + out << R"(/// \brief Number of decimal digits represented by \emph{unsigned long long}.)" << '\n'; + out << "#define ULLONG_DIG " << std::hex << std::showbase << std::numeric_limits::digits10 << '\n'; - out << R"(/// \brief Number of decimal digits necessary to differentiate all values of type \f$unsigned long long\f$.)" << '\n'; - out << "#define ULLONG_DECIMAL_DIG " << "0x" << std::hex << std::numeric_limits::max_digits10 << '\n'; + out << R"(/// \brief Number of decimal digits necessary to differentiate all values of type \emph{unsigned long long}.)" << '\n'; + out << "#define ULLONG_DECIMAL_DIG " << std::hex << std::showbase << std::numeric_limits::max_digits10 << '\n'; - out << R"(/// \brief The radix, or unsigned long longeger base, used to represent a \f$unsigned long long\f$.)" << '\n'; - out << "#define ULLONG_RADIX " << "0x" << std::hex << std::numeric_limits::radix << '\n'; + out << R"(/// \brief The radix, or integer base, used to represent an \emph{unsigned long long}.)" << '\n'; + out << "#define ULLONG_RADIX " << std::hex << std::showbase << std::numeric_limits::radix << '\n'; - out << R"(/// \brief Do arithmetics operations with \f$unsigned long long\f$ trap?)" << '\n'; - out << "#define ULLONG_TRAPS " << "0x" << std::boolalpha << std::numeric_limits::traps << '\n'; + out << R"(/// \brief Do arithmetics operations with \emph{unsigned long long} trap?)" << '\n'; + out << "#define ULLONG_TRAPS " << std::boolalpha << std::numeric_limits::traps << '\n'; - out << R"(/// \brief Smallest finite value of \f$unsigned long long\f$.)" << '\n'; - out << "#define ULLONG_MIN " << "0x" << std::hex << +std::numeric_limits::min() << '\n'; + out << R"(/// \brief Smallest finite value of \emph{unsigned long long}.)" << '\n'; + out << "#define ULLONG_MIN " << std::hex << std::showbase << std::numeric_limits::min() << '\n'; - out << R"(/// \brief Largest finite value of \f$unsigned long long\f$.)" << '\n'; - out << "#define ULLONG_MAX " << "0x" << std::hex << +std::numeric_limits::max() << '\n'; + out << R"(/// \brief Largest finite value of \emph{unsigned long long}.)" << '\n'; + out << "#define ULLONG_MAX " << std::hex << std::showbase << std::numeric_limits::max() << '\n'; out << "" << '\n'; diff --git a/metaprogramming/type_name.h b/metaprogramming/type_name.h index a27c837..58e3bc6 100644 --- a/metaprogramming/type_name.h +++ b/metaprogramming/type_name.h @@ -71,8 +71,8 @@ inline void type_name_h() std::string str = fennec::detail::f(); - size_t heading = str.find("void"); - size_t footing = str.size() - (heading + 4); + const size_t heading = str.find("void"); + const size_t footing = str.size() - (heading + 4); out << "// " << str << std::endl; out << "inline static constexpr size_t type_name_f_heading = " << heading << ";" << std::endl; diff --git a/source/core/event.cpp b/source/core/event.cpp index a010f37..80f1a3b 100644 --- a/source/core/event.cpp +++ b/source/core/event.cpp @@ -45,7 +45,7 @@ void event::handle_events() { // we query the size instead of empty just in case someone decides to run their own thread // and send events from that thread. - size_t n = queue.size(); + const size_t n = queue.size(); for (size_t i = 0; i < n; ++i) { dispatch[i] = queue.pop(); } diff --git a/source/debug/assert_impl.cpp b/source/debug/assert_impl.cpp index a98a7ba..4fadaa2 100644 --- a/source/debug/assert_impl.cpp +++ b/source/debug/assert_impl.cpp @@ -24,7 +24,7 @@ void _assert_callback(const fennec::cstring& expr, const fennec::cstring& file, // Skip // __assert_callback // __assert_impl - fennec::logger::log(fennec::format("" + fennec::logger::log(fennec::logger::fatal, fennec::format("" "Assert failed: \"{}\" \n" "At {}:{} in {} \n" "Description: {} \n" diff --git a/source/filesystem/file.cpp b/source/filesystem/file.cpp index 952709f..52ac5b3 100644 --- a/source/filesystem/file.cpp +++ b/source/filesystem/file.cpp @@ -38,7 +38,7 @@ namespace fennec { -constexpr const cstring fmode_translate(uint8_t mode) { +constexpr cstring fmode_translate(uint8_t mode) { if (not file::is_valid(mode)) { return ""; } @@ -134,15 +134,11 @@ file::file(file&& file) noexcept file& file::operator=(file&& file) noexcept { assert(_error == nullptr, "Attempted Operation on a File in an Errored State"); - close(); - _handle = file._handle; - _path = file._path; - _mode = file._mode; - _error = file._error; - - file._handle = nullptr; - file._path = ""; - file._error = nullptr; + // Swap, if file is temporary it'll close the file for us + swap(_handle, file._handle); + swap(_path, file._path); + swap(_mode, file._mode); + swap(_error, file._error); return *this; } @@ -1060,7 +1056,7 @@ bool file::putc(char c) { } int res; - if ((char)(res = fputc(c, _handle)) != c && res != EOF) { + if (char(res = fputc(c, _handle)) != c && res != EOF) { _error = strerror(errno); return true; } @@ -1078,7 +1074,7 @@ bool file::putwc(wchar_t c) { } int res; - if ((wchar_t)(res = fputwc(c, _handle)) != c && res != EOF) { + if (wchar_t(res = fputwc(c, _handle)) != c && res != EOF) { _error = strerror(errno); return true; } diff --git a/source/platform/interface/platform.cpp b/source/platform/interface/platform.cpp index 74f5d8c..3e2c3d7 100644 --- a/source/platform/interface/platform.cpp +++ b/source/platform/interface/platform.cpp @@ -33,7 +33,7 @@ void platform::initialize() { return; } - logger::log(format("Initializing platform {}", get_type().name())); + logger::log(logger::alert, format("Initializing platform {}", get_type().name())); // Setup Window Manager wmanager = make_unique(this); diff --git a/source/platform/interface/window.cpp b/source/platform/interface/window.cpp index 32a6819..f909744 100644 --- a/source/platform/interface/window.cpp +++ b/source/platform/interface/window.cpp @@ -25,12 +25,15 @@ namespace fennec window::window(display_server* server, const config& conf, window* parent) : server(server), parent(parent) - , root(parent ? parent : this) + , root([&]() -> auto { + window* rt = parent ? parent : this; + while (rt->get_parent() != nullptr and rt->is_popup()) { + rt = root->get_parent(); + } + return rt; + }()) , cfg(conf), state() { state.mode = conf.mode; - while (root->get_parent() != nullptr and root->is_popup()) { - root = root->get_parent(); - } // if parent is null, root will point to this assertf(root != nullptr, "Failed to find appropriate top-level window."); diff --git a/source/platform/linux/wayland/egl/surface.cpp b/source/platform/linux/wayland/egl/surface.cpp index 2b4fa5c..13c7884 100644 --- a/source/platform/linux/wayland/egl/surface.cpp +++ b/source/platform/linux/wayland/egl/surface.cpp @@ -32,15 +32,14 @@ wayland_eglsurface::wayland_eglsurface(wayland_window* win, eglcontext* ctx) win->get_config().rect.size.x, win->get_config().rect.size.y ) ) { - } wayland_eglsurface::~wayland_eglsurface() { - wl_egl_window_destroy(reinterpret_cast(_eglwindow)); + wl_egl_window_destroy(static_cast(_eglwindow)); } void wayland_eglsurface::resize(const ivec2& size) { - wl_egl_window_resize(reinterpret_cast(_eglwindow), size.x, size.y, 0, 0); + wl_egl_window_resize(static_cast(_eglwindow), size.x, size.y, 0, 0); } } diff --git a/source/platform/linux/wayland/lib/sources/wayland-client.c b/source/platform/linux/wayland/lib/sources/wayland-client.c index 2b3959f..8be0fae 100644 --- a/source/platform/linux/wayland/lib/sources/wayland-client.c +++ b/source/platform/linux/wayland/lib/sources/wayland-client.c @@ -1,4 +1,4 @@ -/* Generated by wayland-scanner 1.24.0 */ +/* Generated by wayland-scanner 1.25.0 */ /* * Copyright © 2008-2011 Kristian Høgsberg @@ -124,6 +124,7 @@ static const struct wl_interface *wayland_types[] = { &wl_callback_interface, &wl_region_interface, &wl_region_interface, + &wl_callback_interface, &wl_output_interface, &wl_output_interface, &wl_pointer_interface, @@ -202,11 +203,12 @@ WL_PRIVATE const struct wl_interface wl_callback_interface = { static const struct wl_message wl_compositor_requests[] = { { "create_surface", "n", wayland_types + 10 }, { "create_region", "n", wayland_types + 11 }, + { "release", "7", wayland_types + 0 }, }; WL_PRIVATE const struct wl_interface wl_compositor_interface = { - "wl_compositor", 6, - 2, wl_compositor_requests, + "wl_compositor", 7, + 3, wl_compositor_requests, 0, NULL, }; @@ -266,7 +268,7 @@ static const struct wl_message wl_data_offer_events[] = { }; WL_PRIVATE const struct wl_interface wl_data_offer_interface = { - "wl_data_offer", 3, + "wl_data_offer", 4, 5, wl_data_offer_requests, 3, wl_data_offer_events, }; @@ -287,7 +289,7 @@ static const struct wl_message wl_data_source_events[] = { }; WL_PRIVATE const struct wl_interface wl_data_source_interface = { - "wl_data_source", 3, + "wl_data_source", 4, 3, wl_data_source_requests, 6, wl_data_source_events, }; @@ -308,7 +310,7 @@ static const struct wl_message wl_data_device_events[] = { }; WL_PRIVATE const struct wl_interface wl_data_device_interface = { - "wl_data_device", 3, + "wl_data_device", 4, 3, wl_data_device_requests, 6, wl_data_device_events, }; @@ -316,11 +318,12 @@ WL_PRIVATE const struct wl_interface wl_data_device_interface = { static const struct wl_message wl_data_device_manager_requests[] = { { "create_data_source", "n", wayland_types + 34 }, { "get_data_device", "no", wayland_types + 35 }, + { "release", "4", wayland_types + 0 }, }; WL_PRIVATE const struct wl_interface wl_data_device_manager_interface = { - "wl_data_device_manager", 3, - 2, wl_data_device_manager_requests, + "wl_data_device_manager", 4, + 3, wl_data_device_manager_requests, 0, NULL, }; @@ -371,25 +374,26 @@ static const struct wl_message wl_surface_requests[] = { { "set_buffer_scale", "3i", wayland_types + 0 }, { "damage_buffer", "4iiii", wayland_types + 0 }, { "offset", "5ii", wayland_types + 0 }, + { "get_release", "7n", wayland_types + 64 }, }; static const struct wl_message wl_surface_events[] = { - { "enter", "o", wayland_types + 64 }, - { "leave", "o", wayland_types + 65 }, + { "enter", "o", wayland_types + 65 }, + { "leave", "o", wayland_types + 66 }, { "preferred_buffer_scale", "6i", wayland_types + 0 }, { "preferred_buffer_transform", "6u", wayland_types + 0 }, }; WL_PRIVATE const struct wl_interface wl_surface_interface = { - "wl_surface", 6, - 11, wl_surface_requests, + "wl_surface", 7, + 12, wl_surface_requests, 4, wl_surface_events, }; static const struct wl_message wl_seat_requests[] = { - { "get_pointer", "n", wayland_types + 66 }, - { "get_keyboard", "n", wayland_types + 67 }, - { "get_touch", "n", wayland_types + 68 }, + { "get_pointer", "n", wayland_types + 67 }, + { "get_keyboard", "n", wayland_types + 68 }, + { "get_touch", "n", wayland_types + 69 }, { "release", "5", wayland_types + 0 }, }; @@ -405,13 +409,13 @@ WL_PRIVATE const struct wl_interface wl_seat_interface = { }; static const struct wl_message wl_pointer_requests[] = { - { "set_cursor", "u?oii", wayland_types + 69 }, + { "set_cursor", "u?oii", wayland_types + 70 }, { "release", "3", wayland_types + 0 }, }; static const struct wl_message wl_pointer_events[] = { - { "enter", "uoff", wayland_types + 73 }, - { "leave", "uo", wayland_types + 77 }, + { "enter", "uoff", wayland_types + 74 }, + { "leave", "uo", wayland_types + 78 }, { "motion", "uff", wayland_types + 0 }, { "button", "uuuu", wayland_types + 0 }, { "axis", "uuf", wayland_types + 0 }, @@ -435,8 +439,8 @@ static const struct wl_message wl_keyboard_requests[] = { static const struct wl_message wl_keyboard_events[] = { { "keymap", "uhu", wayland_types + 0 }, - { "enter", "uoa", wayland_types + 79 }, - { "leave", "uo", wayland_types + 82 }, + { "enter", "uoa", wayland_types + 80 }, + { "leave", "uo", wayland_types + 83 }, { "key", "uuuu", wayland_types + 0 }, { "modifiers", "uuuuu", wayland_types + 0 }, { "repeat_info", "4ii", wayland_types + 0 }, @@ -453,7 +457,7 @@ static const struct wl_message wl_touch_requests[] = { }; static const struct wl_message wl_touch_events[] = { - { "down", "uuoiff", wayland_types + 84 }, + { "down", "uuoiff", wayland_types + 85 }, { "up", "uui", wayland_types + 0 }, { "motion", "uiff", wayland_types + 0 }, { "frame", "", wayland_types + 0 }, @@ -494,14 +498,14 @@ static const struct wl_message wl_region_requests[] = { }; WL_PRIVATE const struct wl_interface wl_region_interface = { - "wl_region", 1, + "wl_region", 7, 3, wl_region_requests, 0, NULL, }; static const struct wl_message wl_subcompositor_requests[] = { { "destroy", "", wayland_types + 0 }, - { "get_subsurface", "noo", wayland_types + 90 }, + { "get_subsurface", "noo", wayland_types + 91 }, }; WL_PRIVATE const struct wl_interface wl_subcompositor_interface = { @@ -513,8 +517,8 @@ WL_PRIVATE const struct wl_interface wl_subcompositor_interface = { static const struct wl_message wl_subsurface_requests[] = { { "destroy", "", wayland_types + 0 }, { "set_position", "ii", wayland_types + 0 }, - { "place_above", "o", wayland_types + 93 }, - { "place_below", "o", wayland_types + 94 }, + { "place_above", "o", wayland_types + 94 }, + { "place_below", "o", wayland_types + 95 }, { "set_sync", "", wayland_types + 0 }, { "set_desync", "", wayland_types + 0 }, }; @@ -527,7 +531,7 @@ WL_PRIVATE const struct wl_interface wl_subsurface_interface = { static const struct wl_message wl_fixes_requests[] = { { "destroy", "", wayland_types + 0 }, - { "destroy_registry", "o", wayland_types + 95 }, + { "destroy_registry", "o", wayland_types + 96 }, }; WL_PRIVATE const struct wl_interface wl_fixes_interface = { diff --git a/source/platform/linux/wayland/lib/sources/xdg-shell-client.c b/source/platform/linux/wayland/lib/sources/xdg-shell-client.c index 5a50433..102e36f 100644 --- a/source/platform/linux/wayland/lib/sources/xdg-shell-client.c +++ b/source/platform/linux/wayland/lib/sources/xdg-shell-client.c @@ -1,4 +1,4 @@ -/* Generated by wayland-scanner 1.24.0 */ +/* Generated by wayland-scanner 1.25.0 */ /* * Copyright © 2008-2013 Kristian Høgsberg diff --git a/source/platform/linux/wayland/server.cpp b/source/platform/linux/wayland/server.cpp index 83d788a..4b72ca6 100644 --- a/source/platform/linux/wayland/server.cpp +++ b/source/platform/linux/wayland/server.cpp @@ -234,7 +234,7 @@ void wayland_server::_xdg_listen_ping(void*, xdg_wm_base* xdg, uint32_t serial) #if FENNEC_HAS_LIBDECOR void wayland_server::_libdecor_on_error(struct libdecor*, libdecor_error error, const char* message) { - fennec::logger::log( + fennec::logger::log(logger::error, fennec::format("libdecor error ({}): {}", static_cast(error), fennec::cstring(message, strlen(message))) ); } diff --git a/source/platform/linux/wayland/vulkan/context.cpp b/source/platform/linux/wayland/vulkan/context.cpp new file mode 100644 index 0000000..4ee1198 --- /dev/null +++ b/source/platform/linux/wayland/vulkan/context.cpp @@ -0,0 +1,72 @@ +// ===================================================================================================================== +// fennec, a free and open source game engine +// Copyright © 2025 Medusa Slockbower +// +// This program is free software: you can redistribute it and/or modify +// it under the terms of the GNU General Public License as published by +// the Free Software Foundation, either version 3 of the License, or +// (at your option) any later version. +// +// This program is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. +// +// You should have received a copy of the GNU General Public License +// along with this program. If not, see . +// ===================================================================================================================== + + +#include + +#include +#include +#include + +namespace fennec +{ + +namespace vk +{ + +struct wayland_surface_create_info : VkWaylandSurfaceCreateInfoKHR { + + // Constructor & Destructor ============================================================================================ + public: + wayland_surface_create_info(display_server* server, window* window) + : VkWaylandSurfaceCreateInfoKHR { + .sType = VK_STRUCTURE_TYPE_WAYLAND_SURFACE_CREATE_INFO_KHR, + .pNext = nullptr, + .flags = 0, + .display = static_cast(server->get_native_handle()), + .surface = static_cast(window->get_native_handle()) + } { + } + + operator const VkWaylandSurfaceCreateInfoKHR*() const { + return this; + } + }; + +} + + +wayland_vkcontext::wayland_vkcontext(display_server* display) + : vkcontext(display, extensions) { +} + +wayland_vkcontext::~wayland_vkcontext() { + +} + +gfxsurface* wayland_vkcontext::create_surface(window* window) { + + vk::wayland_surface_create_info info(window->server, window); + + VkSurfaceKHR surface; + vkCreateWaylandSurfaceKHR(*instance, info, nullptr, &surface); + + return new vksurface(window, this, make_unique(surface)); +} + +} diff --git a/source/platform/linux/wayland/window.cpp b/source/platform/linux/wayland/window.cpp index eb19ce6..f08dc1f 100644 --- a/source/platform/linux/wayland/window.cpp +++ b/source/platform/linux/wayland/window.cpp @@ -45,6 +45,10 @@ wayland_window::~wayland_window() { } +void wayland_window::set_size(const ivec2&) { + +} + void wayland_window::initialize() { static constexpr wl_surface_listener surface_listener = { .enter = _wl_surface_listen_enter, @@ -124,7 +128,6 @@ void wayland_window::initialize() { frame_callback = wl_surface_frame(surface); wl_callback_add_listener(frame_callback, &frame_callback_listener, this); - wl_surface_commit(surface); } @@ -202,8 +205,8 @@ bool wayland_window::set_flag(uint8_t flag, bool value) { case flag_borderless: #if FENNEC_HAS_LIBDECOR if (libdecorframe) { - bool vis = libdecor_frame_is_visible(libdecorframe); - bool tgt = not value; + const bool vis = libdecor_frame_is_visible(libdecorframe); + const bool tgt = not value; if (vis != tgt) { libdecor_frame_set_visibility(libdecorframe, tgt); @@ -235,7 +238,7 @@ bool wayland_window::set_flag(uint8_t flag, bool value) { default: - logger::log("Invalid flag passed to window::set_flag."); + logger::log(logger::error, "Invalid flag passed to window::set_flag."); break; } diff --git a/source/platform/opengl/egl/context.cpp b/source/platform/opengl/egl/context.cpp index 2ce2397..82abb39 100644 --- a/source/platform/opengl/egl/context.cpp +++ b/source/platform/opengl/egl/context.cpp @@ -73,7 +73,7 @@ eglcontext::eglcontext(display_server* display) // Initialize EGL assertf(eglInitialize(_egldisplay, &_eglvmajor, &_eglvminor), "Failed to initialize egl."); - logger::log(format("Initialized EGL v{}.{}", _eglvmajor, _eglvminor)); + logger::log(logger::info, format("Initialized EGL v{}.{}", _eglvmajor, _eglvminor)); // Reload EGL bindings assertf(gladLoaderLoadEGL(_egldisplay), "Unable to load EGL Bindings."); @@ -108,7 +108,8 @@ eglcontext::eglcontext(display_server* display) version.minor = _eglvminor; version.patch = 0; version.meta = _eglctype; - logger::log(format("Created OpenGL Context: {} v{}.{}", egl_translate_type(version.meta), version.major, version.minor)); + + logger::log(logger::alert, format("Created OpenGL Context: {} v{}.{}", egl_translate_type(version.meta), version.major, version.minor)); } eglcontext::~eglcontext() { diff --git a/source/platform/opengl/egl/surface.cpp b/source/platform/opengl/egl/surface.cpp index d369a14..fd1f916 100644 --- a/source/platform/opengl/egl/surface.cpp +++ b/source/platform/opengl/egl/surface.cpp @@ -37,8 +37,8 @@ eglsurface::eglsurface(fennec::window* win, eglcontext* ctx, void* eglwindow) ); if (not _eglsurface) { - int32_t err = eglGetError(); - logger::log(format("EGL error: {}", eglErrorString(err))); + const int32_t err = eglGetError(); + logger::log(logger::error, format("EGL error: {}", eglErrorString(err))); } assertf(_eglsurface, "Failed to create EGL surface!"); @@ -46,17 +46,17 @@ eglsurface::eglsurface(fennec::window* win, eglcontext* ctx, void* eglwindow) } eglsurface::~eglsurface() { - eglcontext* ctx = static_cast(context); + eglcontext* ctx = dynamic_cast(context); assertf(eglDestroySurface(ctx->_egldisplay, _eglsurface), "Error destroying EGL surface!"); } void eglsurface::make_current() { - eglcontext* ctx = static_cast(context); + eglcontext* ctx = dynamic_cast(context); assertf(eglMakeCurrent(ctx->_egldisplay, _eglsurface, _eglsurface, ctx->_eglcontext), "Error setting the current surface!"); } void eglsurface::swap() { - eglcontext* ctx = static_cast(context); + eglcontext* ctx = dynamic_cast(context); assertf(eglSwapBuffers(ctx->_egldisplay, _eglsurface), "Error swapping surface buffers!"); } diff --git a/source/platform/vulkan/volk/volk.c b/source/platform/vulkan/volk/volk.c new file mode 100644 index 0000000..ba984c0 --- /dev/null +++ b/source/platform/vulkan/volk/volk.c @@ -0,0 +1,3365 @@ +/* This file is part of volk library; see volk.h for version/license details */ +/* clang-format off */ +#include "volk.h" + +#ifdef _WIN32 + typedef const char* LPCSTR; + typedef struct HINSTANCE__* HINSTANCE; + typedef HINSTANCE HMODULE; + #if defined(_MINWINDEF_) + /* minwindef.h defines FARPROC, and attempting to redefine it may conflict with -Wstrict-prototypes */ + #elif defined(_WIN64) + typedef __int64 (__stdcall* FARPROC)(void); + #else + typedef int (__stdcall* FARPROC)(void); + #endif +#else +# include +#endif + +#ifdef __APPLE__ +# include +#endif + +#ifdef __cplusplus +extern "C" { +#endif + +#ifdef _WIN32 +__declspec(dllimport) HMODULE __stdcall LoadLibraryA(LPCSTR); +__declspec(dllimport) FARPROC __stdcall GetProcAddress(HMODULE, LPCSTR); +__declspec(dllimport) int __stdcall FreeLibrary(HMODULE); +#endif + +#if defined(__GNUC__) +# define VOLK_DISABLE_GCC_PEDANTIC_WARNINGS \ + _Pragma("GCC diagnostic push") \ + _Pragma("GCC diagnostic ignored \"-Wpedantic\"") +# define VOLK_RESTORE_GCC_PEDANTIC_WARNINGS \ + _Pragma("GCC diagnostic pop") +#else +# define VOLK_DISABLE_GCC_PEDANTIC_WARNINGS +# define VOLK_RESTORE_GCC_PEDANTIC_WARNINGS +#endif + +static void* loadedModule = NULL; +static VkInstance loadedInstance = VK_NULL_HANDLE; +static VkDevice loadedDevice = VK_NULL_HANDLE; + +static void volkGenLoadLoader(void* context, PFN_vkVoidFunction (*load)(void*, const char*)); +static void volkGenLoadInstance(void* context, PFN_vkVoidFunction (*load)(void*, const char*)); +static void volkGenLoadDevice(void* context, PFN_vkVoidFunction (*load)(void*, const char*)); +static void volkGenLoadDeviceTable(struct VolkDeviceTable* table, void* context, PFN_vkVoidFunction (*load)(void*, const char*)); + +static PFN_vkVoidFunction vkGetInstanceProcAddrStub(void* context, const char* name) +{ + return vkGetInstanceProcAddr((VkInstance)context, name); +} + +static PFN_vkVoidFunction vkGetDeviceProcAddrStub(void* context, const char* name) +{ + return vkGetDeviceProcAddr((VkDevice)context, name); +} + +static PFN_vkVoidFunction nullProcAddrStub(void* context, const char* name) +{ + (void)context; + (void)name; + return NULL; +} + +VkResult volkInitialize(void) +{ +#if defined(_WIN32) + HMODULE module = LoadLibraryA("vulkan-1.dll"); + if (!module) + return VK_ERROR_INITIALIZATION_FAILED; + + // note: function pointer is cast through void function pointer to silence cast-function-type warning on gcc8 + vkGetInstanceProcAddr = (PFN_vkGetInstanceProcAddr)(void(*)(void))GetProcAddress(module, "vkGetInstanceProcAddr"); +#elif defined(__APPLE__) + void* module = dlopen("libvulkan.dylib", RTLD_NOW | RTLD_LOCAL); + if (!module) + module = dlopen("libvulkan.1.dylib", RTLD_NOW | RTLD_LOCAL); + if (!module) + module = dlopen("libMoltenVK.dylib", RTLD_NOW | RTLD_LOCAL); + // Add support for using Vulkan and MoltenVK in a Framework. App store rules for iOS + // strictly enforce no .dylib's. If they aren't found it just falls through + if (!module) + module = dlopen("vulkan.framework/vulkan", RTLD_NOW | RTLD_LOCAL); + if (!module) + module = dlopen("MoltenVK.framework/MoltenVK", RTLD_NOW | RTLD_LOCAL); + // modern versions of macOS don't search /usr/local/lib automatically contrary to what man dlopen says + // Vulkan SDK uses this as the system-wide installation location, so we're going to fallback to this if all else fails + if (!module && getenv("DYLD_FALLBACK_LIBRARY_PATH") == NULL) + module = dlopen("/usr/local/lib/libvulkan.dylib", RTLD_NOW | RTLD_LOCAL); + if (!module) + return VK_ERROR_INITIALIZATION_FAILED; + + vkGetInstanceProcAddr = (PFN_vkGetInstanceProcAddr)dlsym(module, "vkGetInstanceProcAddr"); +#else + void* module = dlopen("libvulkan.so.1", RTLD_NOW | RTLD_LOCAL); + if (!module) + module = dlopen("libvulkan.so", RTLD_NOW | RTLD_LOCAL); + if (!module) + return VK_ERROR_INITIALIZATION_FAILED; + VOLK_DISABLE_GCC_PEDANTIC_WARNINGS + vkGetInstanceProcAddr = (PFN_vkGetInstanceProcAddr)dlsym(module, "vkGetInstanceProcAddr"); + VOLK_RESTORE_GCC_PEDANTIC_WARNINGS +#endif + + loadedModule = module; + volkGenLoadLoader(NULL, vkGetInstanceProcAddrStub); + + return VK_SUCCESS; +} + +void volkInitializeCustom(PFN_vkGetInstanceProcAddr handler) +{ + vkGetInstanceProcAddr = handler; + + loadedModule = NULL; + volkGenLoadLoader(NULL, vkGetInstanceProcAddrStub); +} + +void volkFinalize(void) +{ + if (loadedModule) + { +#if defined(_WIN32) + FreeLibrary((HMODULE)loadedModule); +#else + dlclose(loadedModule); +#endif + } + + vkGetInstanceProcAddr = NULL; + volkGenLoadLoader(NULL, nullProcAddrStub); + volkGenLoadInstance(NULL, nullProcAddrStub); + volkGenLoadDevice(NULL, nullProcAddrStub); + + loadedModule = NULL; + loadedInstance = VK_NULL_HANDLE; + loadedDevice = VK_NULL_HANDLE; +} + +uint32_t volkGetInstanceVersion(void) +{ +#if defined(VK_VERSION_1_1) + uint32_t apiVersion = 0; + if (vkEnumerateInstanceVersion && vkEnumerateInstanceVersion(&apiVersion) == VK_SUCCESS) + return apiVersion; +#endif + + if (vkCreateInstance) + return VK_API_VERSION_1_0; + + return 0; +} + +void volkLoadInstance(VkInstance instance) +{ + loadedInstance = instance; + volkGenLoadInstance(instance, vkGetInstanceProcAddrStub); + volkGenLoadDevice(instance, vkGetInstanceProcAddrStub); +} + +void volkLoadInstanceOnly(VkInstance instance) +{ + loadedInstance = instance; + volkGenLoadInstance(instance, vkGetInstanceProcAddrStub); +} + +VkInstance volkGetLoadedInstance(void) +{ + return loadedInstance; +} + +void volkLoadDevice(VkDevice device) +{ + loadedDevice = device; + volkGenLoadDevice(device, vkGetDeviceProcAddrStub); +} + +VkDevice volkGetLoadedDevice(void) +{ + return loadedDevice; +} + +void volkLoadDeviceTable(struct VolkDeviceTable* table, VkDevice device) +{ + volkGenLoadDeviceTable(table, device, vkGetDeviceProcAddrStub); +} + +static void volkGenLoadLoader(void* context, PFN_vkVoidFunction (*load)(void*, const char*)) +{ + /* VOLK_GENERATE_LOAD_LOADER */ +#if defined(VK_VERSION_1_0) + vkCreateInstance = (PFN_vkCreateInstance)load(context, "vkCreateInstance"); + vkEnumerateInstanceExtensionProperties = (PFN_vkEnumerateInstanceExtensionProperties)load(context, "vkEnumerateInstanceExtensionProperties"); + vkEnumerateInstanceLayerProperties = (PFN_vkEnumerateInstanceLayerProperties)load(context, "vkEnumerateInstanceLayerProperties"); +#endif /* defined(VK_VERSION_1_0) */ +#if defined(VK_VERSION_1_1) + vkEnumerateInstanceVersion = (PFN_vkEnumerateInstanceVersion)load(context, "vkEnumerateInstanceVersion"); +#endif /* defined(VK_VERSION_1_1) */ + /* VOLK_GENERATE_LOAD_LOADER */ +} + +static void volkGenLoadInstance(void* context, PFN_vkVoidFunction (*load)(void*, const char*)) +{ + /* VOLK_GENERATE_LOAD_INSTANCE */ +#if defined(VK_VERSION_1_0) + vkCreateDevice = (PFN_vkCreateDevice)load(context, "vkCreateDevice"); + vkDestroyInstance = (PFN_vkDestroyInstance)load(context, "vkDestroyInstance"); + vkEnumerateDeviceExtensionProperties = (PFN_vkEnumerateDeviceExtensionProperties)load(context, "vkEnumerateDeviceExtensionProperties"); + vkEnumerateDeviceLayerProperties = (PFN_vkEnumerateDeviceLayerProperties)load(context, "vkEnumerateDeviceLayerProperties"); + vkEnumeratePhysicalDevices = (PFN_vkEnumeratePhysicalDevices)load(context, "vkEnumeratePhysicalDevices"); + vkGetDeviceProcAddr = (PFN_vkGetDeviceProcAddr)load(context, "vkGetDeviceProcAddr"); + vkGetPhysicalDeviceFeatures = (PFN_vkGetPhysicalDeviceFeatures)load(context, "vkGetPhysicalDeviceFeatures"); + vkGetPhysicalDeviceFormatProperties = (PFN_vkGetPhysicalDeviceFormatProperties)load(context, "vkGetPhysicalDeviceFormatProperties"); + vkGetPhysicalDeviceImageFormatProperties = (PFN_vkGetPhysicalDeviceImageFormatProperties)load(context, "vkGetPhysicalDeviceImageFormatProperties"); + vkGetPhysicalDeviceMemoryProperties = (PFN_vkGetPhysicalDeviceMemoryProperties)load(context, "vkGetPhysicalDeviceMemoryProperties"); + vkGetPhysicalDeviceProperties = (PFN_vkGetPhysicalDeviceProperties)load(context, "vkGetPhysicalDeviceProperties"); + vkGetPhysicalDeviceQueueFamilyProperties = (PFN_vkGetPhysicalDeviceQueueFamilyProperties)load(context, "vkGetPhysicalDeviceQueueFamilyProperties"); + vkGetPhysicalDeviceSparseImageFormatProperties = (PFN_vkGetPhysicalDeviceSparseImageFormatProperties)load(context, "vkGetPhysicalDeviceSparseImageFormatProperties"); +#endif /* defined(VK_VERSION_1_0) */ +#if defined(VK_VERSION_1_1) + vkEnumeratePhysicalDeviceGroups = (PFN_vkEnumeratePhysicalDeviceGroups)load(context, "vkEnumeratePhysicalDeviceGroups"); + vkGetPhysicalDeviceExternalBufferProperties = (PFN_vkGetPhysicalDeviceExternalBufferProperties)load(context, "vkGetPhysicalDeviceExternalBufferProperties"); + vkGetPhysicalDeviceExternalFenceProperties = (PFN_vkGetPhysicalDeviceExternalFenceProperties)load(context, "vkGetPhysicalDeviceExternalFenceProperties"); + vkGetPhysicalDeviceExternalSemaphoreProperties = (PFN_vkGetPhysicalDeviceExternalSemaphoreProperties)load(context, "vkGetPhysicalDeviceExternalSemaphoreProperties"); + vkGetPhysicalDeviceFeatures2 = (PFN_vkGetPhysicalDeviceFeatures2)load(context, "vkGetPhysicalDeviceFeatures2"); + vkGetPhysicalDeviceFormatProperties2 = (PFN_vkGetPhysicalDeviceFormatProperties2)load(context, "vkGetPhysicalDeviceFormatProperties2"); + vkGetPhysicalDeviceImageFormatProperties2 = (PFN_vkGetPhysicalDeviceImageFormatProperties2)load(context, "vkGetPhysicalDeviceImageFormatProperties2"); + vkGetPhysicalDeviceMemoryProperties2 = (PFN_vkGetPhysicalDeviceMemoryProperties2)load(context, "vkGetPhysicalDeviceMemoryProperties2"); + vkGetPhysicalDeviceProperties2 = (PFN_vkGetPhysicalDeviceProperties2)load(context, "vkGetPhysicalDeviceProperties2"); + vkGetPhysicalDeviceQueueFamilyProperties2 = (PFN_vkGetPhysicalDeviceQueueFamilyProperties2)load(context, "vkGetPhysicalDeviceQueueFamilyProperties2"); + vkGetPhysicalDeviceSparseImageFormatProperties2 = (PFN_vkGetPhysicalDeviceSparseImageFormatProperties2)load(context, "vkGetPhysicalDeviceSparseImageFormatProperties2"); +#endif /* defined(VK_VERSION_1_1) */ +#if defined(VK_VERSION_1_3) + vkGetPhysicalDeviceToolProperties = (PFN_vkGetPhysicalDeviceToolProperties)load(context, "vkGetPhysicalDeviceToolProperties"); +#endif /* defined(VK_VERSION_1_3) */ +#if defined(VK_EXT_acquire_drm_display) + vkAcquireDrmDisplayEXT = (PFN_vkAcquireDrmDisplayEXT)load(context, "vkAcquireDrmDisplayEXT"); + vkGetDrmDisplayEXT = (PFN_vkGetDrmDisplayEXT)load(context, "vkGetDrmDisplayEXT"); +#endif /* defined(VK_EXT_acquire_drm_display) */ +#if defined(VK_EXT_acquire_xlib_display) + vkAcquireXlibDisplayEXT = (PFN_vkAcquireXlibDisplayEXT)load(context, "vkAcquireXlibDisplayEXT"); + vkGetRandROutputDisplayEXT = (PFN_vkGetRandROutputDisplayEXT)load(context, "vkGetRandROutputDisplayEXT"); +#endif /* defined(VK_EXT_acquire_xlib_display) */ +#if defined(VK_EXT_calibrated_timestamps) + vkGetPhysicalDeviceCalibrateableTimeDomainsEXT = (PFN_vkGetPhysicalDeviceCalibrateableTimeDomainsEXT)load(context, "vkGetPhysicalDeviceCalibrateableTimeDomainsEXT"); +#endif /* defined(VK_EXT_calibrated_timestamps) */ +#if defined(VK_EXT_debug_report) + vkCreateDebugReportCallbackEXT = (PFN_vkCreateDebugReportCallbackEXT)load(context, "vkCreateDebugReportCallbackEXT"); + vkDebugReportMessageEXT = (PFN_vkDebugReportMessageEXT)load(context, "vkDebugReportMessageEXT"); + vkDestroyDebugReportCallbackEXT = (PFN_vkDestroyDebugReportCallbackEXT)load(context, "vkDestroyDebugReportCallbackEXT"); +#endif /* defined(VK_EXT_debug_report) */ +#if defined(VK_EXT_debug_utils) + vkCmdBeginDebugUtilsLabelEXT = (PFN_vkCmdBeginDebugUtilsLabelEXT)load(context, "vkCmdBeginDebugUtilsLabelEXT"); + vkCmdEndDebugUtilsLabelEXT = (PFN_vkCmdEndDebugUtilsLabelEXT)load(context, "vkCmdEndDebugUtilsLabelEXT"); + vkCmdInsertDebugUtilsLabelEXT = (PFN_vkCmdInsertDebugUtilsLabelEXT)load(context, "vkCmdInsertDebugUtilsLabelEXT"); + vkCreateDebugUtilsMessengerEXT = (PFN_vkCreateDebugUtilsMessengerEXT)load(context, "vkCreateDebugUtilsMessengerEXT"); + vkDestroyDebugUtilsMessengerEXT = (PFN_vkDestroyDebugUtilsMessengerEXT)load(context, "vkDestroyDebugUtilsMessengerEXT"); + vkQueueBeginDebugUtilsLabelEXT = (PFN_vkQueueBeginDebugUtilsLabelEXT)load(context, "vkQueueBeginDebugUtilsLabelEXT"); + vkQueueEndDebugUtilsLabelEXT = (PFN_vkQueueEndDebugUtilsLabelEXT)load(context, "vkQueueEndDebugUtilsLabelEXT"); + vkQueueInsertDebugUtilsLabelEXT = (PFN_vkQueueInsertDebugUtilsLabelEXT)load(context, "vkQueueInsertDebugUtilsLabelEXT"); + vkSetDebugUtilsObjectNameEXT = (PFN_vkSetDebugUtilsObjectNameEXT)load(context, "vkSetDebugUtilsObjectNameEXT"); + vkSetDebugUtilsObjectTagEXT = (PFN_vkSetDebugUtilsObjectTagEXT)load(context, "vkSetDebugUtilsObjectTagEXT"); + vkSubmitDebugUtilsMessageEXT = (PFN_vkSubmitDebugUtilsMessageEXT)load(context, "vkSubmitDebugUtilsMessageEXT"); +#endif /* defined(VK_EXT_debug_utils) */ +#if defined(VK_EXT_direct_mode_display) + vkReleaseDisplayEXT = (PFN_vkReleaseDisplayEXT)load(context, "vkReleaseDisplayEXT"); +#endif /* defined(VK_EXT_direct_mode_display) */ +#if defined(VK_EXT_directfb_surface) + vkCreateDirectFBSurfaceEXT = (PFN_vkCreateDirectFBSurfaceEXT)load(context, "vkCreateDirectFBSurfaceEXT"); + vkGetPhysicalDeviceDirectFBPresentationSupportEXT = (PFN_vkGetPhysicalDeviceDirectFBPresentationSupportEXT)load(context, "vkGetPhysicalDeviceDirectFBPresentationSupportEXT"); +#endif /* defined(VK_EXT_directfb_surface) */ +#if defined(VK_EXT_display_surface_counter) + vkGetPhysicalDeviceSurfaceCapabilities2EXT = (PFN_vkGetPhysicalDeviceSurfaceCapabilities2EXT)load(context, "vkGetPhysicalDeviceSurfaceCapabilities2EXT"); +#endif /* defined(VK_EXT_display_surface_counter) */ +#if defined(VK_EXT_full_screen_exclusive) + vkGetPhysicalDeviceSurfacePresentModes2EXT = (PFN_vkGetPhysicalDeviceSurfacePresentModes2EXT)load(context, "vkGetPhysicalDeviceSurfacePresentModes2EXT"); +#endif /* defined(VK_EXT_full_screen_exclusive) */ +#if defined(VK_EXT_headless_surface) + vkCreateHeadlessSurfaceEXT = (PFN_vkCreateHeadlessSurfaceEXT)load(context, "vkCreateHeadlessSurfaceEXT"); +#endif /* defined(VK_EXT_headless_surface) */ +#if defined(VK_EXT_metal_surface) + vkCreateMetalSurfaceEXT = (PFN_vkCreateMetalSurfaceEXT)load(context, "vkCreateMetalSurfaceEXT"); +#endif /* defined(VK_EXT_metal_surface) */ +#if defined(VK_EXT_sample_locations) + vkGetPhysicalDeviceMultisamplePropertiesEXT = (PFN_vkGetPhysicalDeviceMultisamplePropertiesEXT)load(context, "vkGetPhysicalDeviceMultisamplePropertiesEXT"); +#endif /* defined(VK_EXT_sample_locations) */ +#if defined(VK_EXT_tooling_info) + vkGetPhysicalDeviceToolPropertiesEXT = (PFN_vkGetPhysicalDeviceToolPropertiesEXT)load(context, "vkGetPhysicalDeviceToolPropertiesEXT"); +#endif /* defined(VK_EXT_tooling_info) */ +#if defined(VK_FUCHSIA_imagepipe_surface) + vkCreateImagePipeSurfaceFUCHSIA = (PFN_vkCreateImagePipeSurfaceFUCHSIA)load(context, "vkCreateImagePipeSurfaceFUCHSIA"); +#endif /* defined(VK_FUCHSIA_imagepipe_surface) */ +#if defined(VK_GGP_stream_descriptor_surface) + vkCreateStreamDescriptorSurfaceGGP = (PFN_vkCreateStreamDescriptorSurfaceGGP)load(context, "vkCreateStreamDescriptorSurfaceGGP"); +#endif /* defined(VK_GGP_stream_descriptor_surface) */ +#if defined(VK_KHR_android_surface) + vkCreateAndroidSurfaceKHR = (PFN_vkCreateAndroidSurfaceKHR)load(context, "vkCreateAndroidSurfaceKHR"); +#endif /* defined(VK_KHR_android_surface) */ +#if defined(VK_KHR_calibrated_timestamps) + vkGetPhysicalDeviceCalibrateableTimeDomainsKHR = (PFN_vkGetPhysicalDeviceCalibrateableTimeDomainsKHR)load(context, "vkGetPhysicalDeviceCalibrateableTimeDomainsKHR"); +#endif /* defined(VK_KHR_calibrated_timestamps) */ +#if defined(VK_KHR_cooperative_matrix) + vkGetPhysicalDeviceCooperativeMatrixPropertiesKHR = (PFN_vkGetPhysicalDeviceCooperativeMatrixPropertiesKHR)load(context, "vkGetPhysicalDeviceCooperativeMatrixPropertiesKHR"); +#endif /* defined(VK_KHR_cooperative_matrix) */ +#if defined(VK_KHR_device_group_creation) + vkEnumeratePhysicalDeviceGroupsKHR = (PFN_vkEnumeratePhysicalDeviceGroupsKHR)load(context, "vkEnumeratePhysicalDeviceGroupsKHR"); +#endif /* defined(VK_KHR_device_group_creation) */ +#if defined(VK_KHR_display) + vkCreateDisplayModeKHR = (PFN_vkCreateDisplayModeKHR)load(context, "vkCreateDisplayModeKHR"); + vkCreateDisplayPlaneSurfaceKHR = (PFN_vkCreateDisplayPlaneSurfaceKHR)load(context, "vkCreateDisplayPlaneSurfaceKHR"); + vkGetDisplayModePropertiesKHR = (PFN_vkGetDisplayModePropertiesKHR)load(context, "vkGetDisplayModePropertiesKHR"); + vkGetDisplayPlaneCapabilitiesKHR = (PFN_vkGetDisplayPlaneCapabilitiesKHR)load(context, "vkGetDisplayPlaneCapabilitiesKHR"); + vkGetDisplayPlaneSupportedDisplaysKHR = (PFN_vkGetDisplayPlaneSupportedDisplaysKHR)load(context, "vkGetDisplayPlaneSupportedDisplaysKHR"); + vkGetPhysicalDeviceDisplayPlanePropertiesKHR = (PFN_vkGetPhysicalDeviceDisplayPlanePropertiesKHR)load(context, "vkGetPhysicalDeviceDisplayPlanePropertiesKHR"); + vkGetPhysicalDeviceDisplayPropertiesKHR = (PFN_vkGetPhysicalDeviceDisplayPropertiesKHR)load(context, "vkGetPhysicalDeviceDisplayPropertiesKHR"); +#endif /* defined(VK_KHR_display) */ +#if defined(VK_KHR_external_fence_capabilities) + vkGetPhysicalDeviceExternalFencePropertiesKHR = (PFN_vkGetPhysicalDeviceExternalFencePropertiesKHR)load(context, "vkGetPhysicalDeviceExternalFencePropertiesKHR"); +#endif /* defined(VK_KHR_external_fence_capabilities) */ +#if defined(VK_KHR_external_memory_capabilities) + vkGetPhysicalDeviceExternalBufferPropertiesKHR = (PFN_vkGetPhysicalDeviceExternalBufferPropertiesKHR)load(context, "vkGetPhysicalDeviceExternalBufferPropertiesKHR"); +#endif /* defined(VK_KHR_external_memory_capabilities) */ +#if defined(VK_KHR_external_semaphore_capabilities) + vkGetPhysicalDeviceExternalSemaphorePropertiesKHR = (PFN_vkGetPhysicalDeviceExternalSemaphorePropertiesKHR)load(context, "vkGetPhysicalDeviceExternalSemaphorePropertiesKHR"); +#endif /* defined(VK_KHR_external_semaphore_capabilities) */ +#if defined(VK_KHR_fragment_shading_rate) + vkGetPhysicalDeviceFragmentShadingRatesKHR = (PFN_vkGetPhysicalDeviceFragmentShadingRatesKHR)load(context, "vkGetPhysicalDeviceFragmentShadingRatesKHR"); +#endif /* defined(VK_KHR_fragment_shading_rate) */ +#if defined(VK_KHR_get_display_properties2) + vkGetDisplayModeProperties2KHR = (PFN_vkGetDisplayModeProperties2KHR)load(context, "vkGetDisplayModeProperties2KHR"); + vkGetDisplayPlaneCapabilities2KHR = (PFN_vkGetDisplayPlaneCapabilities2KHR)load(context, "vkGetDisplayPlaneCapabilities2KHR"); + vkGetPhysicalDeviceDisplayPlaneProperties2KHR = (PFN_vkGetPhysicalDeviceDisplayPlaneProperties2KHR)load(context, "vkGetPhysicalDeviceDisplayPlaneProperties2KHR"); + vkGetPhysicalDeviceDisplayProperties2KHR = (PFN_vkGetPhysicalDeviceDisplayProperties2KHR)load(context, "vkGetPhysicalDeviceDisplayProperties2KHR"); +#endif /* defined(VK_KHR_get_display_properties2) */ +#if defined(VK_KHR_get_physical_device_properties2) + vkGetPhysicalDeviceFeatures2KHR = (PFN_vkGetPhysicalDeviceFeatures2KHR)load(context, "vkGetPhysicalDeviceFeatures2KHR"); + vkGetPhysicalDeviceFormatProperties2KHR = (PFN_vkGetPhysicalDeviceFormatProperties2KHR)load(context, "vkGetPhysicalDeviceFormatProperties2KHR"); + vkGetPhysicalDeviceImageFormatProperties2KHR = (PFN_vkGetPhysicalDeviceImageFormatProperties2KHR)load(context, "vkGetPhysicalDeviceImageFormatProperties2KHR"); + vkGetPhysicalDeviceMemoryProperties2KHR = (PFN_vkGetPhysicalDeviceMemoryProperties2KHR)load(context, "vkGetPhysicalDeviceMemoryProperties2KHR"); + vkGetPhysicalDeviceProperties2KHR = (PFN_vkGetPhysicalDeviceProperties2KHR)load(context, "vkGetPhysicalDeviceProperties2KHR"); + vkGetPhysicalDeviceQueueFamilyProperties2KHR = (PFN_vkGetPhysicalDeviceQueueFamilyProperties2KHR)load(context, "vkGetPhysicalDeviceQueueFamilyProperties2KHR"); + vkGetPhysicalDeviceSparseImageFormatProperties2KHR = (PFN_vkGetPhysicalDeviceSparseImageFormatProperties2KHR)load(context, "vkGetPhysicalDeviceSparseImageFormatProperties2KHR"); +#endif /* defined(VK_KHR_get_physical_device_properties2) */ +#if defined(VK_KHR_get_surface_capabilities2) + vkGetPhysicalDeviceSurfaceCapabilities2KHR = (PFN_vkGetPhysicalDeviceSurfaceCapabilities2KHR)load(context, "vkGetPhysicalDeviceSurfaceCapabilities2KHR"); + vkGetPhysicalDeviceSurfaceFormats2KHR = (PFN_vkGetPhysicalDeviceSurfaceFormats2KHR)load(context, "vkGetPhysicalDeviceSurfaceFormats2KHR"); +#endif /* defined(VK_KHR_get_surface_capabilities2) */ +#if defined(VK_KHR_performance_query) + vkEnumeratePhysicalDeviceQueueFamilyPerformanceQueryCountersKHR = (PFN_vkEnumeratePhysicalDeviceQueueFamilyPerformanceQueryCountersKHR)load(context, "vkEnumeratePhysicalDeviceQueueFamilyPerformanceQueryCountersKHR"); + vkGetPhysicalDeviceQueueFamilyPerformanceQueryPassesKHR = (PFN_vkGetPhysicalDeviceQueueFamilyPerformanceQueryPassesKHR)load(context, "vkGetPhysicalDeviceQueueFamilyPerformanceQueryPassesKHR"); +#endif /* defined(VK_KHR_performance_query) */ +#if defined(VK_KHR_surface) + vkDestroySurfaceKHR = (PFN_vkDestroySurfaceKHR)load(context, "vkDestroySurfaceKHR"); + vkGetPhysicalDeviceSurfaceCapabilitiesKHR = (PFN_vkGetPhysicalDeviceSurfaceCapabilitiesKHR)load(context, "vkGetPhysicalDeviceSurfaceCapabilitiesKHR"); + vkGetPhysicalDeviceSurfaceFormatsKHR = (PFN_vkGetPhysicalDeviceSurfaceFormatsKHR)load(context, "vkGetPhysicalDeviceSurfaceFormatsKHR"); + vkGetPhysicalDeviceSurfacePresentModesKHR = (PFN_vkGetPhysicalDeviceSurfacePresentModesKHR)load(context, "vkGetPhysicalDeviceSurfacePresentModesKHR"); + vkGetPhysicalDeviceSurfaceSupportKHR = (PFN_vkGetPhysicalDeviceSurfaceSupportKHR)load(context, "vkGetPhysicalDeviceSurfaceSupportKHR"); +#endif /* defined(VK_KHR_surface) */ +#if defined(VK_KHR_video_encode_queue) + vkGetPhysicalDeviceVideoEncodeQualityLevelPropertiesKHR = (PFN_vkGetPhysicalDeviceVideoEncodeQualityLevelPropertiesKHR)load(context, "vkGetPhysicalDeviceVideoEncodeQualityLevelPropertiesKHR"); +#endif /* defined(VK_KHR_video_encode_queue) */ +#if defined(VK_KHR_video_queue) + vkGetPhysicalDeviceVideoCapabilitiesKHR = (PFN_vkGetPhysicalDeviceVideoCapabilitiesKHR)load(context, "vkGetPhysicalDeviceVideoCapabilitiesKHR"); + vkGetPhysicalDeviceVideoFormatPropertiesKHR = (PFN_vkGetPhysicalDeviceVideoFormatPropertiesKHR)load(context, "vkGetPhysicalDeviceVideoFormatPropertiesKHR"); +#endif /* defined(VK_KHR_video_queue) */ +#if defined(VK_KHR_wayland_surface) + vkCreateWaylandSurfaceKHR = (PFN_vkCreateWaylandSurfaceKHR)load(context, "vkCreateWaylandSurfaceKHR"); + vkGetPhysicalDeviceWaylandPresentationSupportKHR = (PFN_vkGetPhysicalDeviceWaylandPresentationSupportKHR)load(context, "vkGetPhysicalDeviceWaylandPresentationSupportKHR"); +#endif /* defined(VK_KHR_wayland_surface) */ +#if defined(VK_KHR_win32_surface) + vkCreateWin32SurfaceKHR = (PFN_vkCreateWin32SurfaceKHR)load(context, "vkCreateWin32SurfaceKHR"); + vkGetPhysicalDeviceWin32PresentationSupportKHR = (PFN_vkGetPhysicalDeviceWin32PresentationSupportKHR)load(context, "vkGetPhysicalDeviceWin32PresentationSupportKHR"); +#endif /* defined(VK_KHR_win32_surface) */ +#if defined(VK_KHR_xcb_surface) + vkCreateXcbSurfaceKHR = (PFN_vkCreateXcbSurfaceKHR)load(context, "vkCreateXcbSurfaceKHR"); + vkGetPhysicalDeviceXcbPresentationSupportKHR = (PFN_vkGetPhysicalDeviceXcbPresentationSupportKHR)load(context, "vkGetPhysicalDeviceXcbPresentationSupportKHR"); +#endif /* defined(VK_KHR_xcb_surface) */ +#if defined(VK_KHR_xlib_surface) + vkCreateXlibSurfaceKHR = (PFN_vkCreateXlibSurfaceKHR)load(context, "vkCreateXlibSurfaceKHR"); + vkGetPhysicalDeviceXlibPresentationSupportKHR = (PFN_vkGetPhysicalDeviceXlibPresentationSupportKHR)load(context, "vkGetPhysicalDeviceXlibPresentationSupportKHR"); +#endif /* defined(VK_KHR_xlib_surface) */ +#if defined(VK_MVK_ios_surface) + vkCreateIOSSurfaceMVK = (PFN_vkCreateIOSSurfaceMVK)load(context, "vkCreateIOSSurfaceMVK"); +#endif /* defined(VK_MVK_ios_surface) */ +#if defined(VK_MVK_macos_surface) + vkCreateMacOSSurfaceMVK = (PFN_vkCreateMacOSSurfaceMVK)load(context, "vkCreateMacOSSurfaceMVK"); +#endif /* defined(VK_MVK_macos_surface) */ +#if defined(VK_NN_vi_surface) + vkCreateViSurfaceNN = (PFN_vkCreateViSurfaceNN)load(context, "vkCreateViSurfaceNN"); +#endif /* defined(VK_NN_vi_surface) */ +#if defined(VK_NV_acquire_winrt_display) + vkAcquireWinrtDisplayNV = (PFN_vkAcquireWinrtDisplayNV)load(context, "vkAcquireWinrtDisplayNV"); + vkGetWinrtDisplayNV = (PFN_vkGetWinrtDisplayNV)load(context, "vkGetWinrtDisplayNV"); +#endif /* defined(VK_NV_acquire_winrt_display) */ +#if defined(VK_NV_cooperative_matrix) + vkGetPhysicalDeviceCooperativeMatrixPropertiesNV = (PFN_vkGetPhysicalDeviceCooperativeMatrixPropertiesNV)load(context, "vkGetPhysicalDeviceCooperativeMatrixPropertiesNV"); +#endif /* defined(VK_NV_cooperative_matrix) */ +#if defined(VK_NV_cooperative_matrix2) + vkGetPhysicalDeviceCooperativeMatrixFlexibleDimensionsPropertiesNV = (PFN_vkGetPhysicalDeviceCooperativeMatrixFlexibleDimensionsPropertiesNV)load(context, "vkGetPhysicalDeviceCooperativeMatrixFlexibleDimensionsPropertiesNV"); +#endif /* defined(VK_NV_cooperative_matrix2) */ +#if defined(VK_NV_coverage_reduction_mode) + vkGetPhysicalDeviceSupportedFramebufferMixedSamplesCombinationsNV = (PFN_vkGetPhysicalDeviceSupportedFramebufferMixedSamplesCombinationsNV)load(context, "vkGetPhysicalDeviceSupportedFramebufferMixedSamplesCombinationsNV"); +#endif /* defined(VK_NV_coverage_reduction_mode) */ +#if defined(VK_NV_external_memory_capabilities) + vkGetPhysicalDeviceExternalImageFormatPropertiesNV = (PFN_vkGetPhysicalDeviceExternalImageFormatPropertiesNV)load(context, "vkGetPhysicalDeviceExternalImageFormatPropertiesNV"); +#endif /* defined(VK_NV_external_memory_capabilities) */ +#if defined(VK_NV_optical_flow) + vkGetPhysicalDeviceOpticalFlowImageFormatsNV = (PFN_vkGetPhysicalDeviceOpticalFlowImageFormatsNV)load(context, "vkGetPhysicalDeviceOpticalFlowImageFormatsNV"); +#endif /* defined(VK_NV_optical_flow) */ +#if defined(VK_QNX_screen_surface) + vkCreateScreenSurfaceQNX = (PFN_vkCreateScreenSurfaceQNX)load(context, "vkCreateScreenSurfaceQNX"); + vkGetPhysicalDeviceScreenPresentationSupportQNX = (PFN_vkGetPhysicalDeviceScreenPresentationSupportQNX)load(context, "vkGetPhysicalDeviceScreenPresentationSupportQNX"); +#endif /* defined(VK_QNX_screen_surface) */ +#if (defined(VK_KHR_device_group) && defined(VK_KHR_surface)) || (defined(VK_KHR_swapchain) && defined(VK_VERSION_1_1)) + vkGetPhysicalDevicePresentRectanglesKHR = (PFN_vkGetPhysicalDevicePresentRectanglesKHR)load(context, "vkGetPhysicalDevicePresentRectanglesKHR"); +#endif /* (defined(VK_KHR_device_group) && defined(VK_KHR_surface)) || (defined(VK_KHR_swapchain) && defined(VK_VERSION_1_1)) */ + /* VOLK_GENERATE_LOAD_INSTANCE */ +} + +static void volkGenLoadDevice(void* context, PFN_vkVoidFunction (*load)(void*, const char*)) +{ + /* VOLK_GENERATE_LOAD_DEVICE */ +#if defined(VK_VERSION_1_0) + vkAllocateCommandBuffers = (PFN_vkAllocateCommandBuffers)load(context, "vkAllocateCommandBuffers"); + vkAllocateDescriptorSets = (PFN_vkAllocateDescriptorSets)load(context, "vkAllocateDescriptorSets"); + vkAllocateMemory = (PFN_vkAllocateMemory)load(context, "vkAllocateMemory"); + vkBeginCommandBuffer = (PFN_vkBeginCommandBuffer)load(context, "vkBeginCommandBuffer"); + vkBindBufferMemory = (PFN_vkBindBufferMemory)load(context, "vkBindBufferMemory"); + vkBindImageMemory = (PFN_vkBindImageMemory)load(context, "vkBindImageMemory"); + vkCmdBeginQuery = (PFN_vkCmdBeginQuery)load(context, "vkCmdBeginQuery"); + vkCmdBeginRenderPass = (PFN_vkCmdBeginRenderPass)load(context, "vkCmdBeginRenderPass"); + vkCmdBindDescriptorSets = (PFN_vkCmdBindDescriptorSets)load(context, "vkCmdBindDescriptorSets"); + vkCmdBindIndexBuffer = (PFN_vkCmdBindIndexBuffer)load(context, "vkCmdBindIndexBuffer"); + vkCmdBindPipeline = (PFN_vkCmdBindPipeline)load(context, "vkCmdBindPipeline"); + vkCmdBindVertexBuffers = (PFN_vkCmdBindVertexBuffers)load(context, "vkCmdBindVertexBuffers"); + vkCmdBlitImage = (PFN_vkCmdBlitImage)load(context, "vkCmdBlitImage"); + vkCmdClearAttachments = (PFN_vkCmdClearAttachments)load(context, "vkCmdClearAttachments"); + vkCmdClearColorImage = (PFN_vkCmdClearColorImage)load(context, "vkCmdClearColorImage"); + vkCmdClearDepthStencilImage = (PFN_vkCmdClearDepthStencilImage)load(context, "vkCmdClearDepthStencilImage"); + vkCmdCopyBuffer = (PFN_vkCmdCopyBuffer)load(context, "vkCmdCopyBuffer"); + vkCmdCopyBufferToImage = (PFN_vkCmdCopyBufferToImage)load(context, "vkCmdCopyBufferToImage"); + vkCmdCopyImage = (PFN_vkCmdCopyImage)load(context, "vkCmdCopyImage"); + vkCmdCopyImageToBuffer = (PFN_vkCmdCopyImageToBuffer)load(context, "vkCmdCopyImageToBuffer"); + vkCmdCopyQueryPoolResults = (PFN_vkCmdCopyQueryPoolResults)load(context, "vkCmdCopyQueryPoolResults"); + vkCmdDispatch = (PFN_vkCmdDispatch)load(context, "vkCmdDispatch"); + vkCmdDispatchIndirect = (PFN_vkCmdDispatchIndirect)load(context, "vkCmdDispatchIndirect"); + vkCmdDraw = (PFN_vkCmdDraw)load(context, "vkCmdDraw"); + vkCmdDrawIndexed = (PFN_vkCmdDrawIndexed)load(context, "vkCmdDrawIndexed"); + vkCmdDrawIndexedIndirect = (PFN_vkCmdDrawIndexedIndirect)load(context, "vkCmdDrawIndexedIndirect"); + vkCmdDrawIndirect = (PFN_vkCmdDrawIndirect)load(context, "vkCmdDrawIndirect"); + vkCmdEndQuery = (PFN_vkCmdEndQuery)load(context, "vkCmdEndQuery"); + vkCmdEndRenderPass = (PFN_vkCmdEndRenderPass)load(context, "vkCmdEndRenderPass"); + vkCmdExecuteCommands = (PFN_vkCmdExecuteCommands)load(context, "vkCmdExecuteCommands"); + vkCmdFillBuffer = (PFN_vkCmdFillBuffer)load(context, "vkCmdFillBuffer"); + vkCmdNextSubpass = (PFN_vkCmdNextSubpass)load(context, "vkCmdNextSubpass"); + vkCmdPipelineBarrier = (PFN_vkCmdPipelineBarrier)load(context, "vkCmdPipelineBarrier"); + vkCmdPushConstants = (PFN_vkCmdPushConstants)load(context, "vkCmdPushConstants"); + vkCmdResetEvent = (PFN_vkCmdResetEvent)load(context, "vkCmdResetEvent"); + vkCmdResetQueryPool = (PFN_vkCmdResetQueryPool)load(context, "vkCmdResetQueryPool"); + vkCmdResolveImage = (PFN_vkCmdResolveImage)load(context, "vkCmdResolveImage"); + vkCmdSetBlendConstants = (PFN_vkCmdSetBlendConstants)load(context, "vkCmdSetBlendConstants"); + vkCmdSetDepthBias = (PFN_vkCmdSetDepthBias)load(context, "vkCmdSetDepthBias"); + vkCmdSetDepthBounds = (PFN_vkCmdSetDepthBounds)load(context, "vkCmdSetDepthBounds"); + vkCmdSetEvent = (PFN_vkCmdSetEvent)load(context, "vkCmdSetEvent"); + vkCmdSetLineWidth = (PFN_vkCmdSetLineWidth)load(context, "vkCmdSetLineWidth"); + vkCmdSetScissor = (PFN_vkCmdSetScissor)load(context, "vkCmdSetScissor"); + vkCmdSetStencilCompareMask = (PFN_vkCmdSetStencilCompareMask)load(context, "vkCmdSetStencilCompareMask"); + vkCmdSetStencilReference = (PFN_vkCmdSetStencilReference)load(context, "vkCmdSetStencilReference"); + vkCmdSetStencilWriteMask = (PFN_vkCmdSetStencilWriteMask)load(context, "vkCmdSetStencilWriteMask"); + vkCmdSetViewport = (PFN_vkCmdSetViewport)load(context, "vkCmdSetViewport"); + vkCmdUpdateBuffer = (PFN_vkCmdUpdateBuffer)load(context, "vkCmdUpdateBuffer"); + vkCmdWaitEvents = (PFN_vkCmdWaitEvents)load(context, "vkCmdWaitEvents"); + vkCmdWriteTimestamp = (PFN_vkCmdWriteTimestamp)load(context, "vkCmdWriteTimestamp"); + vkCreateBuffer = (PFN_vkCreateBuffer)load(context, "vkCreateBuffer"); + vkCreateBufferView = (PFN_vkCreateBufferView)load(context, "vkCreateBufferView"); + vkCreateCommandPool = (PFN_vkCreateCommandPool)load(context, "vkCreateCommandPool"); + vkCreateComputePipelines = (PFN_vkCreateComputePipelines)load(context, "vkCreateComputePipelines"); + vkCreateDescriptorPool = (PFN_vkCreateDescriptorPool)load(context, "vkCreateDescriptorPool"); + vkCreateDescriptorSetLayout = (PFN_vkCreateDescriptorSetLayout)load(context, "vkCreateDescriptorSetLayout"); + vkCreateEvent = (PFN_vkCreateEvent)load(context, "vkCreateEvent"); + vkCreateFence = (PFN_vkCreateFence)load(context, "vkCreateFence"); + vkCreateFramebuffer = (PFN_vkCreateFramebuffer)load(context, "vkCreateFramebuffer"); + vkCreateGraphicsPipelines = (PFN_vkCreateGraphicsPipelines)load(context, "vkCreateGraphicsPipelines"); + vkCreateImage = (PFN_vkCreateImage)load(context, "vkCreateImage"); + vkCreateImageView = (PFN_vkCreateImageView)load(context, "vkCreateImageView"); + vkCreatePipelineCache = (PFN_vkCreatePipelineCache)load(context, "vkCreatePipelineCache"); + vkCreatePipelineLayout = (PFN_vkCreatePipelineLayout)load(context, "vkCreatePipelineLayout"); + vkCreateQueryPool = (PFN_vkCreateQueryPool)load(context, "vkCreateQueryPool"); + vkCreateRenderPass = (PFN_vkCreateRenderPass)load(context, "vkCreateRenderPass"); + vkCreateSampler = (PFN_vkCreateSampler)load(context, "vkCreateSampler"); + vkCreateSemaphore = (PFN_vkCreateSemaphore)load(context, "vkCreateSemaphore"); + vkCreateShaderModule = (PFN_vkCreateShaderModule)load(context, "vkCreateShaderModule"); + vkDestroyBuffer = (PFN_vkDestroyBuffer)load(context, "vkDestroyBuffer"); + vkDestroyBufferView = (PFN_vkDestroyBufferView)load(context, "vkDestroyBufferView"); + vkDestroyCommandPool = (PFN_vkDestroyCommandPool)load(context, "vkDestroyCommandPool"); + vkDestroyDescriptorPool = (PFN_vkDestroyDescriptorPool)load(context, "vkDestroyDescriptorPool"); + vkDestroyDescriptorSetLayout = (PFN_vkDestroyDescriptorSetLayout)load(context, "vkDestroyDescriptorSetLayout"); + vkDestroyDevice = (PFN_vkDestroyDevice)load(context, "vkDestroyDevice"); + vkDestroyEvent = (PFN_vkDestroyEvent)load(context, "vkDestroyEvent"); + vkDestroyFence = (PFN_vkDestroyFence)load(context, "vkDestroyFence"); + vkDestroyFramebuffer = (PFN_vkDestroyFramebuffer)load(context, "vkDestroyFramebuffer"); + vkDestroyImage = (PFN_vkDestroyImage)load(context, "vkDestroyImage"); + vkDestroyImageView = (PFN_vkDestroyImageView)load(context, "vkDestroyImageView"); + vkDestroyPipeline = (PFN_vkDestroyPipeline)load(context, "vkDestroyPipeline"); + vkDestroyPipelineCache = (PFN_vkDestroyPipelineCache)load(context, "vkDestroyPipelineCache"); + vkDestroyPipelineLayout = (PFN_vkDestroyPipelineLayout)load(context, "vkDestroyPipelineLayout"); + vkDestroyQueryPool = (PFN_vkDestroyQueryPool)load(context, "vkDestroyQueryPool"); + vkDestroyRenderPass = (PFN_vkDestroyRenderPass)load(context, "vkDestroyRenderPass"); + vkDestroySampler = (PFN_vkDestroySampler)load(context, "vkDestroySampler"); + vkDestroySemaphore = (PFN_vkDestroySemaphore)load(context, "vkDestroySemaphore"); + vkDestroyShaderModule = (PFN_vkDestroyShaderModule)load(context, "vkDestroyShaderModule"); + vkDeviceWaitIdle = (PFN_vkDeviceWaitIdle)load(context, "vkDeviceWaitIdle"); + vkEndCommandBuffer = (PFN_vkEndCommandBuffer)load(context, "vkEndCommandBuffer"); + vkFlushMappedMemoryRanges = (PFN_vkFlushMappedMemoryRanges)load(context, "vkFlushMappedMemoryRanges"); + vkFreeCommandBuffers = (PFN_vkFreeCommandBuffers)load(context, "vkFreeCommandBuffers"); + vkFreeDescriptorSets = (PFN_vkFreeDescriptorSets)load(context, "vkFreeDescriptorSets"); + vkFreeMemory = (PFN_vkFreeMemory)load(context, "vkFreeMemory"); + vkGetBufferMemoryRequirements = (PFN_vkGetBufferMemoryRequirements)load(context, "vkGetBufferMemoryRequirements"); + vkGetDeviceMemoryCommitment = (PFN_vkGetDeviceMemoryCommitment)load(context, "vkGetDeviceMemoryCommitment"); + vkGetDeviceQueue = (PFN_vkGetDeviceQueue)load(context, "vkGetDeviceQueue"); + vkGetEventStatus = (PFN_vkGetEventStatus)load(context, "vkGetEventStatus"); + vkGetFenceStatus = (PFN_vkGetFenceStatus)load(context, "vkGetFenceStatus"); + vkGetImageMemoryRequirements = (PFN_vkGetImageMemoryRequirements)load(context, "vkGetImageMemoryRequirements"); + vkGetImageSparseMemoryRequirements = (PFN_vkGetImageSparseMemoryRequirements)load(context, "vkGetImageSparseMemoryRequirements"); + vkGetImageSubresourceLayout = (PFN_vkGetImageSubresourceLayout)load(context, "vkGetImageSubresourceLayout"); + vkGetPipelineCacheData = (PFN_vkGetPipelineCacheData)load(context, "vkGetPipelineCacheData"); + vkGetQueryPoolResults = (PFN_vkGetQueryPoolResults)load(context, "vkGetQueryPoolResults"); + vkGetRenderAreaGranularity = (PFN_vkGetRenderAreaGranularity)load(context, "vkGetRenderAreaGranularity"); + vkInvalidateMappedMemoryRanges = (PFN_vkInvalidateMappedMemoryRanges)load(context, "vkInvalidateMappedMemoryRanges"); + vkMapMemory = (PFN_vkMapMemory)load(context, "vkMapMemory"); + vkMergePipelineCaches = (PFN_vkMergePipelineCaches)load(context, "vkMergePipelineCaches"); + vkQueueBindSparse = (PFN_vkQueueBindSparse)load(context, "vkQueueBindSparse"); + vkQueueSubmit = (PFN_vkQueueSubmit)load(context, "vkQueueSubmit"); + vkQueueWaitIdle = (PFN_vkQueueWaitIdle)load(context, "vkQueueWaitIdle"); + vkResetCommandBuffer = (PFN_vkResetCommandBuffer)load(context, "vkResetCommandBuffer"); + vkResetCommandPool = (PFN_vkResetCommandPool)load(context, "vkResetCommandPool"); + vkResetDescriptorPool = (PFN_vkResetDescriptorPool)load(context, "vkResetDescriptorPool"); + vkResetEvent = (PFN_vkResetEvent)load(context, "vkResetEvent"); + vkResetFences = (PFN_vkResetFences)load(context, "vkResetFences"); + vkSetEvent = (PFN_vkSetEvent)load(context, "vkSetEvent"); + vkUnmapMemory = (PFN_vkUnmapMemory)load(context, "vkUnmapMemory"); + vkUpdateDescriptorSets = (PFN_vkUpdateDescriptorSets)load(context, "vkUpdateDescriptorSets"); + vkWaitForFences = (PFN_vkWaitForFences)load(context, "vkWaitForFences"); +#endif /* defined(VK_VERSION_1_0) */ +#if defined(VK_VERSION_1_1) + vkBindBufferMemory2 = (PFN_vkBindBufferMemory2)load(context, "vkBindBufferMemory2"); + vkBindImageMemory2 = (PFN_vkBindImageMemory2)load(context, "vkBindImageMemory2"); + vkCmdDispatchBase = (PFN_vkCmdDispatchBase)load(context, "vkCmdDispatchBase"); + vkCmdSetDeviceMask = (PFN_vkCmdSetDeviceMask)load(context, "vkCmdSetDeviceMask"); + vkCreateDescriptorUpdateTemplate = (PFN_vkCreateDescriptorUpdateTemplate)load(context, "vkCreateDescriptorUpdateTemplate"); + vkCreateSamplerYcbcrConversion = (PFN_vkCreateSamplerYcbcrConversion)load(context, "vkCreateSamplerYcbcrConversion"); + vkDestroyDescriptorUpdateTemplate = (PFN_vkDestroyDescriptorUpdateTemplate)load(context, "vkDestroyDescriptorUpdateTemplate"); + vkDestroySamplerYcbcrConversion = (PFN_vkDestroySamplerYcbcrConversion)load(context, "vkDestroySamplerYcbcrConversion"); + vkGetBufferMemoryRequirements2 = (PFN_vkGetBufferMemoryRequirements2)load(context, "vkGetBufferMemoryRequirements2"); + vkGetDescriptorSetLayoutSupport = (PFN_vkGetDescriptorSetLayoutSupport)load(context, "vkGetDescriptorSetLayoutSupport"); + vkGetDeviceGroupPeerMemoryFeatures = (PFN_vkGetDeviceGroupPeerMemoryFeatures)load(context, "vkGetDeviceGroupPeerMemoryFeatures"); + vkGetDeviceQueue2 = (PFN_vkGetDeviceQueue2)load(context, "vkGetDeviceQueue2"); + vkGetImageMemoryRequirements2 = (PFN_vkGetImageMemoryRequirements2)load(context, "vkGetImageMemoryRequirements2"); + vkGetImageSparseMemoryRequirements2 = (PFN_vkGetImageSparseMemoryRequirements2)load(context, "vkGetImageSparseMemoryRequirements2"); + vkTrimCommandPool = (PFN_vkTrimCommandPool)load(context, "vkTrimCommandPool"); + vkUpdateDescriptorSetWithTemplate = (PFN_vkUpdateDescriptorSetWithTemplate)load(context, "vkUpdateDescriptorSetWithTemplate"); +#endif /* defined(VK_VERSION_1_1) */ +#if defined(VK_VERSION_1_2) + vkCmdBeginRenderPass2 = (PFN_vkCmdBeginRenderPass2)load(context, "vkCmdBeginRenderPass2"); + vkCmdDrawIndexedIndirectCount = (PFN_vkCmdDrawIndexedIndirectCount)load(context, "vkCmdDrawIndexedIndirectCount"); + vkCmdDrawIndirectCount = (PFN_vkCmdDrawIndirectCount)load(context, "vkCmdDrawIndirectCount"); + vkCmdEndRenderPass2 = (PFN_vkCmdEndRenderPass2)load(context, "vkCmdEndRenderPass2"); + vkCmdNextSubpass2 = (PFN_vkCmdNextSubpass2)load(context, "vkCmdNextSubpass2"); + vkCreateRenderPass2 = (PFN_vkCreateRenderPass2)load(context, "vkCreateRenderPass2"); + vkGetBufferDeviceAddress = (PFN_vkGetBufferDeviceAddress)load(context, "vkGetBufferDeviceAddress"); + vkGetBufferOpaqueCaptureAddress = (PFN_vkGetBufferOpaqueCaptureAddress)load(context, "vkGetBufferOpaqueCaptureAddress"); + vkGetDeviceMemoryOpaqueCaptureAddress = (PFN_vkGetDeviceMemoryOpaqueCaptureAddress)load(context, "vkGetDeviceMemoryOpaqueCaptureAddress"); + vkGetSemaphoreCounterValue = (PFN_vkGetSemaphoreCounterValue)load(context, "vkGetSemaphoreCounterValue"); + vkResetQueryPool = (PFN_vkResetQueryPool)load(context, "vkResetQueryPool"); + vkSignalSemaphore = (PFN_vkSignalSemaphore)load(context, "vkSignalSemaphore"); + vkWaitSemaphores = (PFN_vkWaitSemaphores)load(context, "vkWaitSemaphores"); +#endif /* defined(VK_VERSION_1_2) */ +#if defined(VK_VERSION_1_3) + vkCmdBeginRendering = (PFN_vkCmdBeginRendering)load(context, "vkCmdBeginRendering"); + vkCmdBindVertexBuffers2 = (PFN_vkCmdBindVertexBuffers2)load(context, "vkCmdBindVertexBuffers2"); + vkCmdBlitImage2 = (PFN_vkCmdBlitImage2)load(context, "vkCmdBlitImage2"); + vkCmdCopyBuffer2 = (PFN_vkCmdCopyBuffer2)load(context, "vkCmdCopyBuffer2"); + vkCmdCopyBufferToImage2 = (PFN_vkCmdCopyBufferToImage2)load(context, "vkCmdCopyBufferToImage2"); + vkCmdCopyImage2 = (PFN_vkCmdCopyImage2)load(context, "vkCmdCopyImage2"); + vkCmdCopyImageToBuffer2 = (PFN_vkCmdCopyImageToBuffer2)load(context, "vkCmdCopyImageToBuffer2"); + vkCmdEndRendering = (PFN_vkCmdEndRendering)load(context, "vkCmdEndRendering"); + vkCmdPipelineBarrier2 = (PFN_vkCmdPipelineBarrier2)load(context, "vkCmdPipelineBarrier2"); + vkCmdResetEvent2 = (PFN_vkCmdResetEvent2)load(context, "vkCmdResetEvent2"); + vkCmdResolveImage2 = (PFN_vkCmdResolveImage2)load(context, "vkCmdResolveImage2"); + vkCmdSetCullMode = (PFN_vkCmdSetCullMode)load(context, "vkCmdSetCullMode"); + vkCmdSetDepthBiasEnable = (PFN_vkCmdSetDepthBiasEnable)load(context, "vkCmdSetDepthBiasEnable"); + vkCmdSetDepthBoundsTestEnable = (PFN_vkCmdSetDepthBoundsTestEnable)load(context, "vkCmdSetDepthBoundsTestEnable"); + vkCmdSetDepthCompareOp = (PFN_vkCmdSetDepthCompareOp)load(context, "vkCmdSetDepthCompareOp"); + vkCmdSetDepthTestEnable = (PFN_vkCmdSetDepthTestEnable)load(context, "vkCmdSetDepthTestEnable"); + vkCmdSetDepthWriteEnable = (PFN_vkCmdSetDepthWriteEnable)load(context, "vkCmdSetDepthWriteEnable"); + vkCmdSetEvent2 = (PFN_vkCmdSetEvent2)load(context, "vkCmdSetEvent2"); + vkCmdSetFrontFace = (PFN_vkCmdSetFrontFace)load(context, "vkCmdSetFrontFace"); + vkCmdSetPrimitiveRestartEnable = (PFN_vkCmdSetPrimitiveRestartEnable)load(context, "vkCmdSetPrimitiveRestartEnable"); + vkCmdSetPrimitiveTopology = (PFN_vkCmdSetPrimitiveTopology)load(context, "vkCmdSetPrimitiveTopology"); + vkCmdSetRasterizerDiscardEnable = (PFN_vkCmdSetRasterizerDiscardEnable)load(context, "vkCmdSetRasterizerDiscardEnable"); + vkCmdSetScissorWithCount = (PFN_vkCmdSetScissorWithCount)load(context, "vkCmdSetScissorWithCount"); + vkCmdSetStencilOp = (PFN_vkCmdSetStencilOp)load(context, "vkCmdSetStencilOp"); + vkCmdSetStencilTestEnable = (PFN_vkCmdSetStencilTestEnable)load(context, "vkCmdSetStencilTestEnable"); + vkCmdSetViewportWithCount = (PFN_vkCmdSetViewportWithCount)load(context, "vkCmdSetViewportWithCount"); + vkCmdWaitEvents2 = (PFN_vkCmdWaitEvents2)load(context, "vkCmdWaitEvents2"); + vkCmdWriteTimestamp2 = (PFN_vkCmdWriteTimestamp2)load(context, "vkCmdWriteTimestamp2"); + vkCreatePrivateDataSlot = (PFN_vkCreatePrivateDataSlot)load(context, "vkCreatePrivateDataSlot"); + vkDestroyPrivateDataSlot = (PFN_vkDestroyPrivateDataSlot)load(context, "vkDestroyPrivateDataSlot"); + vkGetDeviceBufferMemoryRequirements = (PFN_vkGetDeviceBufferMemoryRequirements)load(context, "vkGetDeviceBufferMemoryRequirements"); + vkGetDeviceImageMemoryRequirements = (PFN_vkGetDeviceImageMemoryRequirements)load(context, "vkGetDeviceImageMemoryRequirements"); + vkGetDeviceImageSparseMemoryRequirements = (PFN_vkGetDeviceImageSparseMemoryRequirements)load(context, "vkGetDeviceImageSparseMemoryRequirements"); + vkGetPrivateData = (PFN_vkGetPrivateData)load(context, "vkGetPrivateData"); + vkQueueSubmit2 = (PFN_vkQueueSubmit2)load(context, "vkQueueSubmit2"); + vkSetPrivateData = (PFN_vkSetPrivateData)load(context, "vkSetPrivateData"); +#endif /* defined(VK_VERSION_1_3) */ +#if defined(VK_VERSION_1_4) + vkCmdBindDescriptorSets2 = (PFN_vkCmdBindDescriptorSets2)load(context, "vkCmdBindDescriptorSets2"); + vkCmdBindIndexBuffer2 = (PFN_vkCmdBindIndexBuffer2)load(context, "vkCmdBindIndexBuffer2"); + vkCmdPushConstants2 = (PFN_vkCmdPushConstants2)load(context, "vkCmdPushConstants2"); + vkCmdPushDescriptorSet = (PFN_vkCmdPushDescriptorSet)load(context, "vkCmdPushDescriptorSet"); + vkCmdPushDescriptorSet2 = (PFN_vkCmdPushDescriptorSet2)load(context, "vkCmdPushDescriptorSet2"); + vkCmdPushDescriptorSetWithTemplate = (PFN_vkCmdPushDescriptorSetWithTemplate)load(context, "vkCmdPushDescriptorSetWithTemplate"); + vkCmdPushDescriptorSetWithTemplate2 = (PFN_vkCmdPushDescriptorSetWithTemplate2)load(context, "vkCmdPushDescriptorSetWithTemplate2"); + vkCmdSetLineStipple = (PFN_vkCmdSetLineStipple)load(context, "vkCmdSetLineStipple"); + vkCmdSetRenderingAttachmentLocations = (PFN_vkCmdSetRenderingAttachmentLocations)load(context, "vkCmdSetRenderingAttachmentLocations"); + vkCmdSetRenderingInputAttachmentIndices = (PFN_vkCmdSetRenderingInputAttachmentIndices)load(context, "vkCmdSetRenderingInputAttachmentIndices"); + vkCopyImageToImage = (PFN_vkCopyImageToImage)load(context, "vkCopyImageToImage"); + vkCopyImageToMemory = (PFN_vkCopyImageToMemory)load(context, "vkCopyImageToMemory"); + vkCopyMemoryToImage = (PFN_vkCopyMemoryToImage)load(context, "vkCopyMemoryToImage"); + vkGetDeviceImageSubresourceLayout = (PFN_vkGetDeviceImageSubresourceLayout)load(context, "vkGetDeviceImageSubresourceLayout"); + vkGetImageSubresourceLayout2 = (PFN_vkGetImageSubresourceLayout2)load(context, "vkGetImageSubresourceLayout2"); + vkGetRenderingAreaGranularity = (PFN_vkGetRenderingAreaGranularity)load(context, "vkGetRenderingAreaGranularity"); + vkMapMemory2 = (PFN_vkMapMemory2)load(context, "vkMapMemory2"); + vkTransitionImageLayout = (PFN_vkTransitionImageLayout)load(context, "vkTransitionImageLayout"); + vkUnmapMemory2 = (PFN_vkUnmapMemory2)load(context, "vkUnmapMemory2"); +#endif /* defined(VK_VERSION_1_4) */ +#if defined(VK_AMDX_shader_enqueue) + vkCmdDispatchGraphAMDX = (PFN_vkCmdDispatchGraphAMDX)load(context, "vkCmdDispatchGraphAMDX"); + vkCmdDispatchGraphIndirectAMDX = (PFN_vkCmdDispatchGraphIndirectAMDX)load(context, "vkCmdDispatchGraphIndirectAMDX"); + vkCmdDispatchGraphIndirectCountAMDX = (PFN_vkCmdDispatchGraphIndirectCountAMDX)load(context, "vkCmdDispatchGraphIndirectCountAMDX"); + vkCmdInitializeGraphScratchMemoryAMDX = (PFN_vkCmdInitializeGraphScratchMemoryAMDX)load(context, "vkCmdInitializeGraphScratchMemoryAMDX"); + vkCreateExecutionGraphPipelinesAMDX = (PFN_vkCreateExecutionGraphPipelinesAMDX)load(context, "vkCreateExecutionGraphPipelinesAMDX"); + vkGetExecutionGraphPipelineNodeIndexAMDX = (PFN_vkGetExecutionGraphPipelineNodeIndexAMDX)load(context, "vkGetExecutionGraphPipelineNodeIndexAMDX"); + vkGetExecutionGraphPipelineScratchSizeAMDX = (PFN_vkGetExecutionGraphPipelineScratchSizeAMDX)load(context, "vkGetExecutionGraphPipelineScratchSizeAMDX"); +#endif /* defined(VK_AMDX_shader_enqueue) */ +#if defined(VK_AMD_anti_lag) + vkAntiLagUpdateAMD = (PFN_vkAntiLagUpdateAMD)load(context, "vkAntiLagUpdateAMD"); +#endif /* defined(VK_AMD_anti_lag) */ +#if defined(VK_AMD_buffer_marker) + vkCmdWriteBufferMarkerAMD = (PFN_vkCmdWriteBufferMarkerAMD)load(context, "vkCmdWriteBufferMarkerAMD"); +#endif /* defined(VK_AMD_buffer_marker) */ +#if defined(VK_AMD_buffer_marker) && (defined(VK_VERSION_1_3) || defined(VK_KHR_synchronization2)) + vkCmdWriteBufferMarker2AMD = (PFN_vkCmdWriteBufferMarker2AMD)load(context, "vkCmdWriteBufferMarker2AMD"); +#endif /* defined(VK_AMD_buffer_marker) && (defined(VK_VERSION_1_3) || defined(VK_KHR_synchronization2)) */ +#if defined(VK_AMD_display_native_hdr) + vkSetLocalDimmingAMD = (PFN_vkSetLocalDimmingAMD)load(context, "vkSetLocalDimmingAMD"); +#endif /* defined(VK_AMD_display_native_hdr) */ +#if defined(VK_AMD_draw_indirect_count) + vkCmdDrawIndexedIndirectCountAMD = (PFN_vkCmdDrawIndexedIndirectCountAMD)load(context, "vkCmdDrawIndexedIndirectCountAMD"); + vkCmdDrawIndirectCountAMD = (PFN_vkCmdDrawIndirectCountAMD)load(context, "vkCmdDrawIndirectCountAMD"); +#endif /* defined(VK_AMD_draw_indirect_count) */ +#if defined(VK_AMD_shader_info) + vkGetShaderInfoAMD = (PFN_vkGetShaderInfoAMD)load(context, "vkGetShaderInfoAMD"); +#endif /* defined(VK_AMD_shader_info) */ +#if defined(VK_ANDROID_external_memory_android_hardware_buffer) + vkGetAndroidHardwareBufferPropertiesANDROID = (PFN_vkGetAndroidHardwareBufferPropertiesANDROID)load(context, "vkGetAndroidHardwareBufferPropertiesANDROID"); + vkGetMemoryAndroidHardwareBufferANDROID = (PFN_vkGetMemoryAndroidHardwareBufferANDROID)load(context, "vkGetMemoryAndroidHardwareBufferANDROID"); +#endif /* defined(VK_ANDROID_external_memory_android_hardware_buffer) */ +#if defined(VK_EXT_attachment_feedback_loop_dynamic_state) + vkCmdSetAttachmentFeedbackLoopEnableEXT = (PFN_vkCmdSetAttachmentFeedbackLoopEnableEXT)load(context, "vkCmdSetAttachmentFeedbackLoopEnableEXT"); +#endif /* defined(VK_EXT_attachment_feedback_loop_dynamic_state) */ +#if defined(VK_EXT_buffer_device_address) + vkGetBufferDeviceAddressEXT = (PFN_vkGetBufferDeviceAddressEXT)load(context, "vkGetBufferDeviceAddressEXT"); +#endif /* defined(VK_EXT_buffer_device_address) */ +#if defined(VK_EXT_calibrated_timestamps) + vkGetCalibratedTimestampsEXT = (PFN_vkGetCalibratedTimestampsEXT)load(context, "vkGetCalibratedTimestampsEXT"); +#endif /* defined(VK_EXT_calibrated_timestamps) */ +#if defined(VK_EXT_color_write_enable) + vkCmdSetColorWriteEnableEXT = (PFN_vkCmdSetColorWriteEnableEXT)load(context, "vkCmdSetColorWriteEnableEXT"); +#endif /* defined(VK_EXT_color_write_enable) */ +#if defined(VK_EXT_conditional_rendering) + vkCmdBeginConditionalRenderingEXT = (PFN_vkCmdBeginConditionalRenderingEXT)load(context, "vkCmdBeginConditionalRenderingEXT"); + vkCmdEndConditionalRenderingEXT = (PFN_vkCmdEndConditionalRenderingEXT)load(context, "vkCmdEndConditionalRenderingEXT"); +#endif /* defined(VK_EXT_conditional_rendering) */ +#if defined(VK_EXT_debug_marker) + vkCmdDebugMarkerBeginEXT = (PFN_vkCmdDebugMarkerBeginEXT)load(context, "vkCmdDebugMarkerBeginEXT"); + vkCmdDebugMarkerEndEXT = (PFN_vkCmdDebugMarkerEndEXT)load(context, "vkCmdDebugMarkerEndEXT"); + vkCmdDebugMarkerInsertEXT = (PFN_vkCmdDebugMarkerInsertEXT)load(context, "vkCmdDebugMarkerInsertEXT"); + vkDebugMarkerSetObjectNameEXT = (PFN_vkDebugMarkerSetObjectNameEXT)load(context, "vkDebugMarkerSetObjectNameEXT"); + vkDebugMarkerSetObjectTagEXT = (PFN_vkDebugMarkerSetObjectTagEXT)load(context, "vkDebugMarkerSetObjectTagEXT"); +#endif /* defined(VK_EXT_debug_marker) */ +#if defined(VK_EXT_depth_bias_control) + vkCmdSetDepthBias2EXT = (PFN_vkCmdSetDepthBias2EXT)load(context, "vkCmdSetDepthBias2EXT"); +#endif /* defined(VK_EXT_depth_bias_control) */ +#if defined(VK_EXT_descriptor_buffer) + vkCmdBindDescriptorBufferEmbeddedSamplersEXT = (PFN_vkCmdBindDescriptorBufferEmbeddedSamplersEXT)load(context, "vkCmdBindDescriptorBufferEmbeddedSamplersEXT"); + vkCmdBindDescriptorBuffersEXT = (PFN_vkCmdBindDescriptorBuffersEXT)load(context, "vkCmdBindDescriptorBuffersEXT"); + vkCmdSetDescriptorBufferOffsetsEXT = (PFN_vkCmdSetDescriptorBufferOffsetsEXT)load(context, "vkCmdSetDescriptorBufferOffsetsEXT"); + vkGetBufferOpaqueCaptureDescriptorDataEXT = (PFN_vkGetBufferOpaqueCaptureDescriptorDataEXT)load(context, "vkGetBufferOpaqueCaptureDescriptorDataEXT"); + vkGetDescriptorEXT = (PFN_vkGetDescriptorEXT)load(context, "vkGetDescriptorEXT"); + vkGetDescriptorSetLayoutBindingOffsetEXT = (PFN_vkGetDescriptorSetLayoutBindingOffsetEXT)load(context, "vkGetDescriptorSetLayoutBindingOffsetEXT"); + vkGetDescriptorSetLayoutSizeEXT = (PFN_vkGetDescriptorSetLayoutSizeEXT)load(context, "vkGetDescriptorSetLayoutSizeEXT"); + vkGetImageOpaqueCaptureDescriptorDataEXT = (PFN_vkGetImageOpaqueCaptureDescriptorDataEXT)load(context, "vkGetImageOpaqueCaptureDescriptorDataEXT"); + vkGetImageViewOpaqueCaptureDescriptorDataEXT = (PFN_vkGetImageViewOpaqueCaptureDescriptorDataEXT)load(context, "vkGetImageViewOpaqueCaptureDescriptorDataEXT"); + vkGetSamplerOpaqueCaptureDescriptorDataEXT = (PFN_vkGetSamplerOpaqueCaptureDescriptorDataEXT)load(context, "vkGetSamplerOpaqueCaptureDescriptorDataEXT"); +#endif /* defined(VK_EXT_descriptor_buffer) */ +#if defined(VK_EXT_descriptor_buffer) && (defined(VK_KHR_acceleration_structure) || defined(VK_NV_ray_tracing)) + vkGetAccelerationStructureOpaqueCaptureDescriptorDataEXT = (PFN_vkGetAccelerationStructureOpaqueCaptureDescriptorDataEXT)load(context, "vkGetAccelerationStructureOpaqueCaptureDescriptorDataEXT"); +#endif /* defined(VK_EXT_descriptor_buffer) && (defined(VK_KHR_acceleration_structure) || defined(VK_NV_ray_tracing)) */ +#if defined(VK_EXT_device_fault) + vkGetDeviceFaultInfoEXT = (PFN_vkGetDeviceFaultInfoEXT)load(context, "vkGetDeviceFaultInfoEXT"); +#endif /* defined(VK_EXT_device_fault) */ +#if defined(VK_EXT_device_generated_commands) + vkCmdExecuteGeneratedCommandsEXT = (PFN_vkCmdExecuteGeneratedCommandsEXT)load(context, "vkCmdExecuteGeneratedCommandsEXT"); + vkCmdPreprocessGeneratedCommandsEXT = (PFN_vkCmdPreprocessGeneratedCommandsEXT)load(context, "vkCmdPreprocessGeneratedCommandsEXT"); + vkCreateIndirectCommandsLayoutEXT = (PFN_vkCreateIndirectCommandsLayoutEXT)load(context, "vkCreateIndirectCommandsLayoutEXT"); + vkCreateIndirectExecutionSetEXT = (PFN_vkCreateIndirectExecutionSetEXT)load(context, "vkCreateIndirectExecutionSetEXT"); + vkDestroyIndirectCommandsLayoutEXT = (PFN_vkDestroyIndirectCommandsLayoutEXT)load(context, "vkDestroyIndirectCommandsLayoutEXT"); + vkDestroyIndirectExecutionSetEXT = (PFN_vkDestroyIndirectExecutionSetEXT)load(context, "vkDestroyIndirectExecutionSetEXT"); + vkGetGeneratedCommandsMemoryRequirementsEXT = (PFN_vkGetGeneratedCommandsMemoryRequirementsEXT)load(context, "vkGetGeneratedCommandsMemoryRequirementsEXT"); + vkUpdateIndirectExecutionSetPipelineEXT = (PFN_vkUpdateIndirectExecutionSetPipelineEXT)load(context, "vkUpdateIndirectExecutionSetPipelineEXT"); + vkUpdateIndirectExecutionSetShaderEXT = (PFN_vkUpdateIndirectExecutionSetShaderEXT)load(context, "vkUpdateIndirectExecutionSetShaderEXT"); +#endif /* defined(VK_EXT_device_generated_commands) */ +#if defined(VK_EXT_discard_rectangles) + vkCmdSetDiscardRectangleEXT = (PFN_vkCmdSetDiscardRectangleEXT)load(context, "vkCmdSetDiscardRectangleEXT"); +#endif /* defined(VK_EXT_discard_rectangles) */ +#if defined(VK_EXT_discard_rectangles) && VK_EXT_DISCARD_RECTANGLES_SPEC_VERSION >= 2 + vkCmdSetDiscardRectangleEnableEXT = (PFN_vkCmdSetDiscardRectangleEnableEXT)load(context, "vkCmdSetDiscardRectangleEnableEXT"); + vkCmdSetDiscardRectangleModeEXT = (PFN_vkCmdSetDiscardRectangleModeEXT)load(context, "vkCmdSetDiscardRectangleModeEXT"); +#endif /* defined(VK_EXT_discard_rectangles) && VK_EXT_DISCARD_RECTANGLES_SPEC_VERSION >= 2 */ +#if defined(VK_EXT_display_control) + vkDisplayPowerControlEXT = (PFN_vkDisplayPowerControlEXT)load(context, "vkDisplayPowerControlEXT"); + vkGetSwapchainCounterEXT = (PFN_vkGetSwapchainCounterEXT)load(context, "vkGetSwapchainCounterEXT"); + vkRegisterDeviceEventEXT = (PFN_vkRegisterDeviceEventEXT)load(context, "vkRegisterDeviceEventEXT"); + vkRegisterDisplayEventEXT = (PFN_vkRegisterDisplayEventEXT)load(context, "vkRegisterDisplayEventEXT"); +#endif /* defined(VK_EXT_display_control) */ +#if defined(VK_EXT_external_memory_host) + vkGetMemoryHostPointerPropertiesEXT = (PFN_vkGetMemoryHostPointerPropertiesEXT)load(context, "vkGetMemoryHostPointerPropertiesEXT"); +#endif /* defined(VK_EXT_external_memory_host) */ +#if defined(VK_EXT_full_screen_exclusive) + vkAcquireFullScreenExclusiveModeEXT = (PFN_vkAcquireFullScreenExclusiveModeEXT)load(context, "vkAcquireFullScreenExclusiveModeEXT"); + vkReleaseFullScreenExclusiveModeEXT = (PFN_vkReleaseFullScreenExclusiveModeEXT)load(context, "vkReleaseFullScreenExclusiveModeEXT"); +#endif /* defined(VK_EXT_full_screen_exclusive) */ +#if defined(VK_EXT_full_screen_exclusive) && (defined(VK_KHR_device_group) || defined(VK_VERSION_1_1)) + vkGetDeviceGroupSurfacePresentModes2EXT = (PFN_vkGetDeviceGroupSurfacePresentModes2EXT)load(context, "vkGetDeviceGroupSurfacePresentModes2EXT"); +#endif /* defined(VK_EXT_full_screen_exclusive) && (defined(VK_KHR_device_group) || defined(VK_VERSION_1_1)) */ +#if defined(VK_EXT_hdr_metadata) + vkSetHdrMetadataEXT = (PFN_vkSetHdrMetadataEXT)load(context, "vkSetHdrMetadataEXT"); +#endif /* defined(VK_EXT_hdr_metadata) */ +#if defined(VK_EXT_host_image_copy) + vkCopyImageToImageEXT = (PFN_vkCopyImageToImageEXT)load(context, "vkCopyImageToImageEXT"); + vkCopyImageToMemoryEXT = (PFN_vkCopyImageToMemoryEXT)load(context, "vkCopyImageToMemoryEXT"); + vkCopyMemoryToImageEXT = (PFN_vkCopyMemoryToImageEXT)load(context, "vkCopyMemoryToImageEXT"); + vkTransitionImageLayoutEXT = (PFN_vkTransitionImageLayoutEXT)load(context, "vkTransitionImageLayoutEXT"); +#endif /* defined(VK_EXT_host_image_copy) */ +#if defined(VK_EXT_host_query_reset) + vkResetQueryPoolEXT = (PFN_vkResetQueryPoolEXT)load(context, "vkResetQueryPoolEXT"); +#endif /* defined(VK_EXT_host_query_reset) */ +#if defined(VK_EXT_image_drm_format_modifier) + vkGetImageDrmFormatModifierPropertiesEXT = (PFN_vkGetImageDrmFormatModifierPropertiesEXT)load(context, "vkGetImageDrmFormatModifierPropertiesEXT"); +#endif /* defined(VK_EXT_image_drm_format_modifier) */ +#if defined(VK_EXT_line_rasterization) + vkCmdSetLineStippleEXT = (PFN_vkCmdSetLineStippleEXT)load(context, "vkCmdSetLineStippleEXT"); +#endif /* defined(VK_EXT_line_rasterization) */ +#if defined(VK_EXT_mesh_shader) + vkCmdDrawMeshTasksEXT = (PFN_vkCmdDrawMeshTasksEXT)load(context, "vkCmdDrawMeshTasksEXT"); + vkCmdDrawMeshTasksIndirectEXT = (PFN_vkCmdDrawMeshTasksIndirectEXT)load(context, "vkCmdDrawMeshTasksIndirectEXT"); +#endif /* defined(VK_EXT_mesh_shader) */ +#if defined(VK_EXT_mesh_shader) && (defined(VK_KHR_draw_indirect_count) || defined(VK_VERSION_1_2)) + vkCmdDrawMeshTasksIndirectCountEXT = (PFN_vkCmdDrawMeshTasksIndirectCountEXT)load(context, "vkCmdDrawMeshTasksIndirectCountEXT"); +#endif /* defined(VK_EXT_mesh_shader) && (defined(VK_KHR_draw_indirect_count) || defined(VK_VERSION_1_2)) */ +#if defined(VK_EXT_metal_objects) + vkExportMetalObjectsEXT = (PFN_vkExportMetalObjectsEXT)load(context, "vkExportMetalObjectsEXT"); +#endif /* defined(VK_EXT_metal_objects) */ +#if defined(VK_EXT_multi_draw) + vkCmdDrawMultiEXT = (PFN_vkCmdDrawMultiEXT)load(context, "vkCmdDrawMultiEXT"); + vkCmdDrawMultiIndexedEXT = (PFN_vkCmdDrawMultiIndexedEXT)load(context, "vkCmdDrawMultiIndexedEXT"); +#endif /* defined(VK_EXT_multi_draw) */ +#if defined(VK_EXT_opacity_micromap) + vkBuildMicromapsEXT = (PFN_vkBuildMicromapsEXT)load(context, "vkBuildMicromapsEXT"); + vkCmdBuildMicromapsEXT = (PFN_vkCmdBuildMicromapsEXT)load(context, "vkCmdBuildMicromapsEXT"); + vkCmdCopyMemoryToMicromapEXT = (PFN_vkCmdCopyMemoryToMicromapEXT)load(context, "vkCmdCopyMemoryToMicromapEXT"); + vkCmdCopyMicromapEXT = (PFN_vkCmdCopyMicromapEXT)load(context, "vkCmdCopyMicromapEXT"); + vkCmdCopyMicromapToMemoryEXT = (PFN_vkCmdCopyMicromapToMemoryEXT)load(context, "vkCmdCopyMicromapToMemoryEXT"); + vkCmdWriteMicromapsPropertiesEXT = (PFN_vkCmdWriteMicromapsPropertiesEXT)load(context, "vkCmdWriteMicromapsPropertiesEXT"); + vkCopyMemoryToMicromapEXT = (PFN_vkCopyMemoryToMicromapEXT)load(context, "vkCopyMemoryToMicromapEXT"); + vkCopyMicromapEXT = (PFN_vkCopyMicromapEXT)load(context, "vkCopyMicromapEXT"); + vkCopyMicromapToMemoryEXT = (PFN_vkCopyMicromapToMemoryEXT)load(context, "vkCopyMicromapToMemoryEXT"); + vkCreateMicromapEXT = (PFN_vkCreateMicromapEXT)load(context, "vkCreateMicromapEXT"); + vkDestroyMicromapEXT = (PFN_vkDestroyMicromapEXT)load(context, "vkDestroyMicromapEXT"); + vkGetDeviceMicromapCompatibilityEXT = (PFN_vkGetDeviceMicromapCompatibilityEXT)load(context, "vkGetDeviceMicromapCompatibilityEXT"); + vkGetMicromapBuildSizesEXT = (PFN_vkGetMicromapBuildSizesEXT)load(context, "vkGetMicromapBuildSizesEXT"); + vkWriteMicromapsPropertiesEXT = (PFN_vkWriteMicromapsPropertiesEXT)load(context, "vkWriteMicromapsPropertiesEXT"); +#endif /* defined(VK_EXT_opacity_micromap) */ +#if defined(VK_EXT_pageable_device_local_memory) + vkSetDeviceMemoryPriorityEXT = (PFN_vkSetDeviceMemoryPriorityEXT)load(context, "vkSetDeviceMemoryPriorityEXT"); +#endif /* defined(VK_EXT_pageable_device_local_memory) */ +#if defined(VK_EXT_pipeline_properties) + vkGetPipelinePropertiesEXT = (PFN_vkGetPipelinePropertiesEXT)load(context, "vkGetPipelinePropertiesEXT"); +#endif /* defined(VK_EXT_pipeline_properties) */ +#if defined(VK_EXT_private_data) + vkCreatePrivateDataSlotEXT = (PFN_vkCreatePrivateDataSlotEXT)load(context, "vkCreatePrivateDataSlotEXT"); + vkDestroyPrivateDataSlotEXT = (PFN_vkDestroyPrivateDataSlotEXT)load(context, "vkDestroyPrivateDataSlotEXT"); + vkGetPrivateDataEXT = (PFN_vkGetPrivateDataEXT)load(context, "vkGetPrivateDataEXT"); + vkSetPrivateDataEXT = (PFN_vkSetPrivateDataEXT)load(context, "vkSetPrivateDataEXT"); +#endif /* defined(VK_EXT_private_data) */ +#if defined(VK_EXT_sample_locations) + vkCmdSetSampleLocationsEXT = (PFN_vkCmdSetSampleLocationsEXT)load(context, "vkCmdSetSampleLocationsEXT"); +#endif /* defined(VK_EXT_sample_locations) */ +#if defined(VK_EXT_shader_module_identifier) + vkGetShaderModuleCreateInfoIdentifierEXT = (PFN_vkGetShaderModuleCreateInfoIdentifierEXT)load(context, "vkGetShaderModuleCreateInfoIdentifierEXT"); + vkGetShaderModuleIdentifierEXT = (PFN_vkGetShaderModuleIdentifierEXT)load(context, "vkGetShaderModuleIdentifierEXT"); +#endif /* defined(VK_EXT_shader_module_identifier) */ +#if defined(VK_EXT_shader_object) + vkCmdBindShadersEXT = (PFN_vkCmdBindShadersEXT)load(context, "vkCmdBindShadersEXT"); + vkCreateShadersEXT = (PFN_vkCreateShadersEXT)load(context, "vkCreateShadersEXT"); + vkDestroyShaderEXT = (PFN_vkDestroyShaderEXT)load(context, "vkDestroyShaderEXT"); + vkGetShaderBinaryDataEXT = (PFN_vkGetShaderBinaryDataEXT)load(context, "vkGetShaderBinaryDataEXT"); +#endif /* defined(VK_EXT_shader_object) */ +#if defined(VK_EXT_swapchain_maintenance1) + vkReleaseSwapchainImagesEXT = (PFN_vkReleaseSwapchainImagesEXT)load(context, "vkReleaseSwapchainImagesEXT"); +#endif /* defined(VK_EXT_swapchain_maintenance1) */ +#if defined(VK_EXT_transform_feedback) + vkCmdBeginQueryIndexedEXT = (PFN_vkCmdBeginQueryIndexedEXT)load(context, "vkCmdBeginQueryIndexedEXT"); + vkCmdBeginTransformFeedbackEXT = (PFN_vkCmdBeginTransformFeedbackEXT)load(context, "vkCmdBeginTransformFeedbackEXT"); + vkCmdBindTransformFeedbackBuffersEXT = (PFN_vkCmdBindTransformFeedbackBuffersEXT)load(context, "vkCmdBindTransformFeedbackBuffersEXT"); + vkCmdDrawIndirectByteCountEXT = (PFN_vkCmdDrawIndirectByteCountEXT)load(context, "vkCmdDrawIndirectByteCountEXT"); + vkCmdEndQueryIndexedEXT = (PFN_vkCmdEndQueryIndexedEXT)load(context, "vkCmdEndQueryIndexedEXT"); + vkCmdEndTransformFeedbackEXT = (PFN_vkCmdEndTransformFeedbackEXT)load(context, "vkCmdEndTransformFeedbackEXT"); +#endif /* defined(VK_EXT_transform_feedback) */ +#if defined(VK_EXT_validation_cache) + vkCreateValidationCacheEXT = (PFN_vkCreateValidationCacheEXT)load(context, "vkCreateValidationCacheEXT"); + vkDestroyValidationCacheEXT = (PFN_vkDestroyValidationCacheEXT)load(context, "vkDestroyValidationCacheEXT"); + vkGetValidationCacheDataEXT = (PFN_vkGetValidationCacheDataEXT)load(context, "vkGetValidationCacheDataEXT"); + vkMergeValidationCachesEXT = (PFN_vkMergeValidationCachesEXT)load(context, "vkMergeValidationCachesEXT"); +#endif /* defined(VK_EXT_validation_cache) */ +#if defined(VK_FUCHSIA_buffer_collection) + vkCreateBufferCollectionFUCHSIA = (PFN_vkCreateBufferCollectionFUCHSIA)load(context, "vkCreateBufferCollectionFUCHSIA"); + vkDestroyBufferCollectionFUCHSIA = (PFN_vkDestroyBufferCollectionFUCHSIA)load(context, "vkDestroyBufferCollectionFUCHSIA"); + vkGetBufferCollectionPropertiesFUCHSIA = (PFN_vkGetBufferCollectionPropertiesFUCHSIA)load(context, "vkGetBufferCollectionPropertiesFUCHSIA"); + vkSetBufferCollectionBufferConstraintsFUCHSIA = (PFN_vkSetBufferCollectionBufferConstraintsFUCHSIA)load(context, "vkSetBufferCollectionBufferConstraintsFUCHSIA"); + vkSetBufferCollectionImageConstraintsFUCHSIA = (PFN_vkSetBufferCollectionImageConstraintsFUCHSIA)load(context, "vkSetBufferCollectionImageConstraintsFUCHSIA"); +#endif /* defined(VK_FUCHSIA_buffer_collection) */ +#if defined(VK_FUCHSIA_external_memory) + vkGetMemoryZirconHandleFUCHSIA = (PFN_vkGetMemoryZirconHandleFUCHSIA)load(context, "vkGetMemoryZirconHandleFUCHSIA"); + vkGetMemoryZirconHandlePropertiesFUCHSIA = (PFN_vkGetMemoryZirconHandlePropertiesFUCHSIA)load(context, "vkGetMemoryZirconHandlePropertiesFUCHSIA"); +#endif /* defined(VK_FUCHSIA_external_memory) */ +#if defined(VK_FUCHSIA_external_semaphore) + vkGetSemaphoreZirconHandleFUCHSIA = (PFN_vkGetSemaphoreZirconHandleFUCHSIA)load(context, "vkGetSemaphoreZirconHandleFUCHSIA"); + vkImportSemaphoreZirconHandleFUCHSIA = (PFN_vkImportSemaphoreZirconHandleFUCHSIA)load(context, "vkImportSemaphoreZirconHandleFUCHSIA"); +#endif /* defined(VK_FUCHSIA_external_semaphore) */ +#if defined(VK_GOOGLE_display_timing) + vkGetPastPresentationTimingGOOGLE = (PFN_vkGetPastPresentationTimingGOOGLE)load(context, "vkGetPastPresentationTimingGOOGLE"); + vkGetRefreshCycleDurationGOOGLE = (PFN_vkGetRefreshCycleDurationGOOGLE)load(context, "vkGetRefreshCycleDurationGOOGLE"); +#endif /* defined(VK_GOOGLE_display_timing) */ +#if defined(VK_HUAWEI_cluster_culling_shader) + vkCmdDrawClusterHUAWEI = (PFN_vkCmdDrawClusterHUAWEI)load(context, "vkCmdDrawClusterHUAWEI"); + vkCmdDrawClusterIndirectHUAWEI = (PFN_vkCmdDrawClusterIndirectHUAWEI)load(context, "vkCmdDrawClusterIndirectHUAWEI"); +#endif /* defined(VK_HUAWEI_cluster_culling_shader) */ +#if defined(VK_HUAWEI_invocation_mask) + vkCmdBindInvocationMaskHUAWEI = (PFN_vkCmdBindInvocationMaskHUAWEI)load(context, "vkCmdBindInvocationMaskHUAWEI"); +#endif /* defined(VK_HUAWEI_invocation_mask) */ +#if defined(VK_HUAWEI_subpass_shading) && VK_HUAWEI_SUBPASS_SHADING_SPEC_VERSION >= 2 + vkGetDeviceSubpassShadingMaxWorkgroupSizeHUAWEI = (PFN_vkGetDeviceSubpassShadingMaxWorkgroupSizeHUAWEI)load(context, "vkGetDeviceSubpassShadingMaxWorkgroupSizeHUAWEI"); +#endif /* defined(VK_HUAWEI_subpass_shading) && VK_HUAWEI_SUBPASS_SHADING_SPEC_VERSION >= 2 */ +#if defined(VK_HUAWEI_subpass_shading) + vkCmdSubpassShadingHUAWEI = (PFN_vkCmdSubpassShadingHUAWEI)load(context, "vkCmdSubpassShadingHUAWEI"); +#endif /* defined(VK_HUAWEI_subpass_shading) */ +#if defined(VK_INTEL_performance_query) + vkAcquirePerformanceConfigurationINTEL = (PFN_vkAcquirePerformanceConfigurationINTEL)load(context, "vkAcquirePerformanceConfigurationINTEL"); + vkCmdSetPerformanceMarkerINTEL = (PFN_vkCmdSetPerformanceMarkerINTEL)load(context, "vkCmdSetPerformanceMarkerINTEL"); + vkCmdSetPerformanceOverrideINTEL = (PFN_vkCmdSetPerformanceOverrideINTEL)load(context, "vkCmdSetPerformanceOverrideINTEL"); + vkCmdSetPerformanceStreamMarkerINTEL = (PFN_vkCmdSetPerformanceStreamMarkerINTEL)load(context, "vkCmdSetPerformanceStreamMarkerINTEL"); + vkGetPerformanceParameterINTEL = (PFN_vkGetPerformanceParameterINTEL)load(context, "vkGetPerformanceParameterINTEL"); + vkInitializePerformanceApiINTEL = (PFN_vkInitializePerformanceApiINTEL)load(context, "vkInitializePerformanceApiINTEL"); + vkQueueSetPerformanceConfigurationINTEL = (PFN_vkQueueSetPerformanceConfigurationINTEL)load(context, "vkQueueSetPerformanceConfigurationINTEL"); + vkReleasePerformanceConfigurationINTEL = (PFN_vkReleasePerformanceConfigurationINTEL)load(context, "vkReleasePerformanceConfigurationINTEL"); + vkUninitializePerformanceApiINTEL = (PFN_vkUninitializePerformanceApiINTEL)load(context, "vkUninitializePerformanceApiINTEL"); +#endif /* defined(VK_INTEL_performance_query) */ +#if defined(VK_KHR_acceleration_structure) + vkBuildAccelerationStructuresKHR = (PFN_vkBuildAccelerationStructuresKHR)load(context, "vkBuildAccelerationStructuresKHR"); + vkCmdBuildAccelerationStructuresIndirectKHR = (PFN_vkCmdBuildAccelerationStructuresIndirectKHR)load(context, "vkCmdBuildAccelerationStructuresIndirectKHR"); + vkCmdBuildAccelerationStructuresKHR = (PFN_vkCmdBuildAccelerationStructuresKHR)load(context, "vkCmdBuildAccelerationStructuresKHR"); + vkCmdCopyAccelerationStructureKHR = (PFN_vkCmdCopyAccelerationStructureKHR)load(context, "vkCmdCopyAccelerationStructureKHR"); + vkCmdCopyAccelerationStructureToMemoryKHR = (PFN_vkCmdCopyAccelerationStructureToMemoryKHR)load(context, "vkCmdCopyAccelerationStructureToMemoryKHR"); + vkCmdCopyMemoryToAccelerationStructureKHR = (PFN_vkCmdCopyMemoryToAccelerationStructureKHR)load(context, "vkCmdCopyMemoryToAccelerationStructureKHR"); + vkCmdWriteAccelerationStructuresPropertiesKHR = (PFN_vkCmdWriteAccelerationStructuresPropertiesKHR)load(context, "vkCmdWriteAccelerationStructuresPropertiesKHR"); + vkCopyAccelerationStructureKHR = (PFN_vkCopyAccelerationStructureKHR)load(context, "vkCopyAccelerationStructureKHR"); + vkCopyAccelerationStructureToMemoryKHR = (PFN_vkCopyAccelerationStructureToMemoryKHR)load(context, "vkCopyAccelerationStructureToMemoryKHR"); + vkCopyMemoryToAccelerationStructureKHR = (PFN_vkCopyMemoryToAccelerationStructureKHR)load(context, "vkCopyMemoryToAccelerationStructureKHR"); + vkCreateAccelerationStructureKHR = (PFN_vkCreateAccelerationStructureKHR)load(context, "vkCreateAccelerationStructureKHR"); + vkDestroyAccelerationStructureKHR = (PFN_vkDestroyAccelerationStructureKHR)load(context, "vkDestroyAccelerationStructureKHR"); + vkGetAccelerationStructureBuildSizesKHR = (PFN_vkGetAccelerationStructureBuildSizesKHR)load(context, "vkGetAccelerationStructureBuildSizesKHR"); + vkGetAccelerationStructureDeviceAddressKHR = (PFN_vkGetAccelerationStructureDeviceAddressKHR)load(context, "vkGetAccelerationStructureDeviceAddressKHR"); + vkGetDeviceAccelerationStructureCompatibilityKHR = (PFN_vkGetDeviceAccelerationStructureCompatibilityKHR)load(context, "vkGetDeviceAccelerationStructureCompatibilityKHR"); + vkWriteAccelerationStructuresPropertiesKHR = (PFN_vkWriteAccelerationStructuresPropertiesKHR)load(context, "vkWriteAccelerationStructuresPropertiesKHR"); +#endif /* defined(VK_KHR_acceleration_structure) */ +#if defined(VK_KHR_bind_memory2) + vkBindBufferMemory2KHR = (PFN_vkBindBufferMemory2KHR)load(context, "vkBindBufferMemory2KHR"); + vkBindImageMemory2KHR = (PFN_vkBindImageMemory2KHR)load(context, "vkBindImageMemory2KHR"); +#endif /* defined(VK_KHR_bind_memory2) */ +#if defined(VK_KHR_buffer_device_address) + vkGetBufferDeviceAddressKHR = (PFN_vkGetBufferDeviceAddressKHR)load(context, "vkGetBufferDeviceAddressKHR"); + vkGetBufferOpaqueCaptureAddressKHR = (PFN_vkGetBufferOpaqueCaptureAddressKHR)load(context, "vkGetBufferOpaqueCaptureAddressKHR"); + vkGetDeviceMemoryOpaqueCaptureAddressKHR = (PFN_vkGetDeviceMemoryOpaqueCaptureAddressKHR)load(context, "vkGetDeviceMemoryOpaqueCaptureAddressKHR"); +#endif /* defined(VK_KHR_buffer_device_address) */ +#if defined(VK_KHR_calibrated_timestamps) + vkGetCalibratedTimestampsKHR = (PFN_vkGetCalibratedTimestampsKHR)load(context, "vkGetCalibratedTimestampsKHR"); +#endif /* defined(VK_KHR_calibrated_timestamps) */ +#if defined(VK_KHR_copy_commands2) + vkCmdBlitImage2KHR = (PFN_vkCmdBlitImage2KHR)load(context, "vkCmdBlitImage2KHR"); + vkCmdCopyBuffer2KHR = (PFN_vkCmdCopyBuffer2KHR)load(context, "vkCmdCopyBuffer2KHR"); + vkCmdCopyBufferToImage2KHR = (PFN_vkCmdCopyBufferToImage2KHR)load(context, "vkCmdCopyBufferToImage2KHR"); + vkCmdCopyImage2KHR = (PFN_vkCmdCopyImage2KHR)load(context, "vkCmdCopyImage2KHR"); + vkCmdCopyImageToBuffer2KHR = (PFN_vkCmdCopyImageToBuffer2KHR)load(context, "vkCmdCopyImageToBuffer2KHR"); + vkCmdResolveImage2KHR = (PFN_vkCmdResolveImage2KHR)load(context, "vkCmdResolveImage2KHR"); +#endif /* defined(VK_KHR_copy_commands2) */ +#if defined(VK_KHR_create_renderpass2) + vkCmdBeginRenderPass2KHR = (PFN_vkCmdBeginRenderPass2KHR)load(context, "vkCmdBeginRenderPass2KHR"); + vkCmdEndRenderPass2KHR = (PFN_vkCmdEndRenderPass2KHR)load(context, "vkCmdEndRenderPass2KHR"); + vkCmdNextSubpass2KHR = (PFN_vkCmdNextSubpass2KHR)load(context, "vkCmdNextSubpass2KHR"); + vkCreateRenderPass2KHR = (PFN_vkCreateRenderPass2KHR)load(context, "vkCreateRenderPass2KHR"); +#endif /* defined(VK_KHR_create_renderpass2) */ +#if defined(VK_KHR_deferred_host_operations) + vkCreateDeferredOperationKHR = (PFN_vkCreateDeferredOperationKHR)load(context, "vkCreateDeferredOperationKHR"); + vkDeferredOperationJoinKHR = (PFN_vkDeferredOperationJoinKHR)load(context, "vkDeferredOperationJoinKHR"); + vkDestroyDeferredOperationKHR = (PFN_vkDestroyDeferredOperationKHR)load(context, "vkDestroyDeferredOperationKHR"); + vkGetDeferredOperationMaxConcurrencyKHR = (PFN_vkGetDeferredOperationMaxConcurrencyKHR)load(context, "vkGetDeferredOperationMaxConcurrencyKHR"); + vkGetDeferredOperationResultKHR = (PFN_vkGetDeferredOperationResultKHR)load(context, "vkGetDeferredOperationResultKHR"); +#endif /* defined(VK_KHR_deferred_host_operations) */ +#if defined(VK_KHR_descriptor_update_template) + vkCreateDescriptorUpdateTemplateKHR = (PFN_vkCreateDescriptorUpdateTemplateKHR)load(context, "vkCreateDescriptorUpdateTemplateKHR"); + vkDestroyDescriptorUpdateTemplateKHR = (PFN_vkDestroyDescriptorUpdateTemplateKHR)load(context, "vkDestroyDescriptorUpdateTemplateKHR"); + vkUpdateDescriptorSetWithTemplateKHR = (PFN_vkUpdateDescriptorSetWithTemplateKHR)load(context, "vkUpdateDescriptorSetWithTemplateKHR"); +#endif /* defined(VK_KHR_descriptor_update_template) */ +#if defined(VK_KHR_device_group) + vkCmdDispatchBaseKHR = (PFN_vkCmdDispatchBaseKHR)load(context, "vkCmdDispatchBaseKHR"); + vkCmdSetDeviceMaskKHR = (PFN_vkCmdSetDeviceMaskKHR)load(context, "vkCmdSetDeviceMaskKHR"); + vkGetDeviceGroupPeerMemoryFeaturesKHR = (PFN_vkGetDeviceGroupPeerMemoryFeaturesKHR)load(context, "vkGetDeviceGroupPeerMemoryFeaturesKHR"); +#endif /* defined(VK_KHR_device_group) */ +#if defined(VK_KHR_display_swapchain) + vkCreateSharedSwapchainsKHR = (PFN_vkCreateSharedSwapchainsKHR)load(context, "vkCreateSharedSwapchainsKHR"); +#endif /* defined(VK_KHR_display_swapchain) */ +#if defined(VK_KHR_draw_indirect_count) + vkCmdDrawIndexedIndirectCountKHR = (PFN_vkCmdDrawIndexedIndirectCountKHR)load(context, "vkCmdDrawIndexedIndirectCountKHR"); + vkCmdDrawIndirectCountKHR = (PFN_vkCmdDrawIndirectCountKHR)load(context, "vkCmdDrawIndirectCountKHR"); +#endif /* defined(VK_KHR_draw_indirect_count) */ +#if defined(VK_KHR_dynamic_rendering) + vkCmdBeginRenderingKHR = (PFN_vkCmdBeginRenderingKHR)load(context, "vkCmdBeginRenderingKHR"); + vkCmdEndRenderingKHR = (PFN_vkCmdEndRenderingKHR)load(context, "vkCmdEndRenderingKHR"); +#endif /* defined(VK_KHR_dynamic_rendering) */ +#if defined(VK_KHR_dynamic_rendering_local_read) + vkCmdSetRenderingAttachmentLocationsKHR = (PFN_vkCmdSetRenderingAttachmentLocationsKHR)load(context, "vkCmdSetRenderingAttachmentLocationsKHR"); + vkCmdSetRenderingInputAttachmentIndicesKHR = (PFN_vkCmdSetRenderingInputAttachmentIndicesKHR)load(context, "vkCmdSetRenderingInputAttachmentIndicesKHR"); +#endif /* defined(VK_KHR_dynamic_rendering_local_read) */ +#if defined(VK_KHR_external_fence_fd) + vkGetFenceFdKHR = (PFN_vkGetFenceFdKHR)load(context, "vkGetFenceFdKHR"); + vkImportFenceFdKHR = (PFN_vkImportFenceFdKHR)load(context, "vkImportFenceFdKHR"); +#endif /* defined(VK_KHR_external_fence_fd) */ +#if defined(VK_KHR_external_fence_win32) + vkGetFenceWin32HandleKHR = (PFN_vkGetFenceWin32HandleKHR)load(context, "vkGetFenceWin32HandleKHR"); + vkImportFenceWin32HandleKHR = (PFN_vkImportFenceWin32HandleKHR)load(context, "vkImportFenceWin32HandleKHR"); +#endif /* defined(VK_KHR_external_fence_win32) */ +#if defined(VK_KHR_external_memory_fd) + vkGetMemoryFdKHR = (PFN_vkGetMemoryFdKHR)load(context, "vkGetMemoryFdKHR"); + vkGetMemoryFdPropertiesKHR = (PFN_vkGetMemoryFdPropertiesKHR)load(context, "vkGetMemoryFdPropertiesKHR"); +#endif /* defined(VK_KHR_external_memory_fd) */ +#if defined(VK_KHR_external_memory_win32) + vkGetMemoryWin32HandleKHR = (PFN_vkGetMemoryWin32HandleKHR)load(context, "vkGetMemoryWin32HandleKHR"); + vkGetMemoryWin32HandlePropertiesKHR = (PFN_vkGetMemoryWin32HandlePropertiesKHR)load(context, "vkGetMemoryWin32HandlePropertiesKHR"); +#endif /* defined(VK_KHR_external_memory_win32) */ +#if defined(VK_KHR_external_semaphore_fd) + vkGetSemaphoreFdKHR = (PFN_vkGetSemaphoreFdKHR)load(context, "vkGetSemaphoreFdKHR"); + vkImportSemaphoreFdKHR = (PFN_vkImportSemaphoreFdKHR)load(context, "vkImportSemaphoreFdKHR"); +#endif /* defined(VK_KHR_external_semaphore_fd) */ +#if defined(VK_KHR_external_semaphore_win32) + vkGetSemaphoreWin32HandleKHR = (PFN_vkGetSemaphoreWin32HandleKHR)load(context, "vkGetSemaphoreWin32HandleKHR"); + vkImportSemaphoreWin32HandleKHR = (PFN_vkImportSemaphoreWin32HandleKHR)load(context, "vkImportSemaphoreWin32HandleKHR"); +#endif /* defined(VK_KHR_external_semaphore_win32) */ +#if defined(VK_KHR_fragment_shading_rate) + vkCmdSetFragmentShadingRateKHR = (PFN_vkCmdSetFragmentShadingRateKHR)load(context, "vkCmdSetFragmentShadingRateKHR"); +#endif /* defined(VK_KHR_fragment_shading_rate) */ +#if defined(VK_KHR_get_memory_requirements2) + vkGetBufferMemoryRequirements2KHR = (PFN_vkGetBufferMemoryRequirements2KHR)load(context, "vkGetBufferMemoryRequirements2KHR"); + vkGetImageMemoryRequirements2KHR = (PFN_vkGetImageMemoryRequirements2KHR)load(context, "vkGetImageMemoryRequirements2KHR"); + vkGetImageSparseMemoryRequirements2KHR = (PFN_vkGetImageSparseMemoryRequirements2KHR)load(context, "vkGetImageSparseMemoryRequirements2KHR"); +#endif /* defined(VK_KHR_get_memory_requirements2) */ +#if defined(VK_KHR_line_rasterization) + vkCmdSetLineStippleKHR = (PFN_vkCmdSetLineStippleKHR)load(context, "vkCmdSetLineStippleKHR"); +#endif /* defined(VK_KHR_line_rasterization) */ +#if defined(VK_KHR_maintenance1) + vkTrimCommandPoolKHR = (PFN_vkTrimCommandPoolKHR)load(context, "vkTrimCommandPoolKHR"); +#endif /* defined(VK_KHR_maintenance1) */ +#if defined(VK_KHR_maintenance3) + vkGetDescriptorSetLayoutSupportKHR = (PFN_vkGetDescriptorSetLayoutSupportKHR)load(context, "vkGetDescriptorSetLayoutSupportKHR"); +#endif /* defined(VK_KHR_maintenance3) */ +#if defined(VK_KHR_maintenance4) + vkGetDeviceBufferMemoryRequirementsKHR = (PFN_vkGetDeviceBufferMemoryRequirementsKHR)load(context, "vkGetDeviceBufferMemoryRequirementsKHR"); + vkGetDeviceImageMemoryRequirementsKHR = (PFN_vkGetDeviceImageMemoryRequirementsKHR)load(context, "vkGetDeviceImageMemoryRequirementsKHR"); + vkGetDeviceImageSparseMemoryRequirementsKHR = (PFN_vkGetDeviceImageSparseMemoryRequirementsKHR)load(context, "vkGetDeviceImageSparseMemoryRequirementsKHR"); +#endif /* defined(VK_KHR_maintenance4) */ +#if defined(VK_KHR_maintenance5) + vkCmdBindIndexBuffer2KHR = (PFN_vkCmdBindIndexBuffer2KHR)load(context, "vkCmdBindIndexBuffer2KHR"); + vkGetDeviceImageSubresourceLayoutKHR = (PFN_vkGetDeviceImageSubresourceLayoutKHR)load(context, "vkGetDeviceImageSubresourceLayoutKHR"); + vkGetImageSubresourceLayout2KHR = (PFN_vkGetImageSubresourceLayout2KHR)load(context, "vkGetImageSubresourceLayout2KHR"); + vkGetRenderingAreaGranularityKHR = (PFN_vkGetRenderingAreaGranularityKHR)load(context, "vkGetRenderingAreaGranularityKHR"); +#endif /* defined(VK_KHR_maintenance5) */ +#if defined(VK_KHR_maintenance6) + vkCmdBindDescriptorSets2KHR = (PFN_vkCmdBindDescriptorSets2KHR)load(context, "vkCmdBindDescriptorSets2KHR"); + vkCmdPushConstants2KHR = (PFN_vkCmdPushConstants2KHR)load(context, "vkCmdPushConstants2KHR"); +#endif /* defined(VK_KHR_maintenance6) */ +#if defined(VK_KHR_maintenance6) && defined(VK_KHR_push_descriptor) + vkCmdPushDescriptorSet2KHR = (PFN_vkCmdPushDescriptorSet2KHR)load(context, "vkCmdPushDescriptorSet2KHR"); + vkCmdPushDescriptorSetWithTemplate2KHR = (PFN_vkCmdPushDescriptorSetWithTemplate2KHR)load(context, "vkCmdPushDescriptorSetWithTemplate2KHR"); +#endif /* defined(VK_KHR_maintenance6) && defined(VK_KHR_push_descriptor) */ +#if defined(VK_KHR_maintenance6) && defined(VK_EXT_descriptor_buffer) + vkCmdBindDescriptorBufferEmbeddedSamplers2EXT = (PFN_vkCmdBindDescriptorBufferEmbeddedSamplers2EXT)load(context, "vkCmdBindDescriptorBufferEmbeddedSamplers2EXT"); + vkCmdSetDescriptorBufferOffsets2EXT = (PFN_vkCmdSetDescriptorBufferOffsets2EXT)load(context, "vkCmdSetDescriptorBufferOffsets2EXT"); +#endif /* defined(VK_KHR_maintenance6) && defined(VK_EXT_descriptor_buffer) */ +#if defined(VK_KHR_map_memory2) + vkMapMemory2KHR = (PFN_vkMapMemory2KHR)load(context, "vkMapMemory2KHR"); + vkUnmapMemory2KHR = (PFN_vkUnmapMemory2KHR)load(context, "vkUnmapMemory2KHR"); +#endif /* defined(VK_KHR_map_memory2) */ +#if defined(VK_KHR_performance_query) + vkAcquireProfilingLockKHR = (PFN_vkAcquireProfilingLockKHR)load(context, "vkAcquireProfilingLockKHR"); + vkReleaseProfilingLockKHR = (PFN_vkReleaseProfilingLockKHR)load(context, "vkReleaseProfilingLockKHR"); +#endif /* defined(VK_KHR_performance_query) */ +#if defined(VK_KHR_pipeline_binary) + vkCreatePipelineBinariesKHR = (PFN_vkCreatePipelineBinariesKHR)load(context, "vkCreatePipelineBinariesKHR"); + vkDestroyPipelineBinaryKHR = (PFN_vkDestroyPipelineBinaryKHR)load(context, "vkDestroyPipelineBinaryKHR"); + vkGetPipelineBinaryDataKHR = (PFN_vkGetPipelineBinaryDataKHR)load(context, "vkGetPipelineBinaryDataKHR"); + vkGetPipelineKeyKHR = (PFN_vkGetPipelineKeyKHR)load(context, "vkGetPipelineKeyKHR"); + vkReleaseCapturedPipelineDataKHR = (PFN_vkReleaseCapturedPipelineDataKHR)load(context, "vkReleaseCapturedPipelineDataKHR"); +#endif /* defined(VK_KHR_pipeline_binary) */ +#if defined(VK_KHR_pipeline_executable_properties) + vkGetPipelineExecutableInternalRepresentationsKHR = (PFN_vkGetPipelineExecutableInternalRepresentationsKHR)load(context, "vkGetPipelineExecutableInternalRepresentationsKHR"); + vkGetPipelineExecutablePropertiesKHR = (PFN_vkGetPipelineExecutablePropertiesKHR)load(context, "vkGetPipelineExecutablePropertiesKHR"); + vkGetPipelineExecutableStatisticsKHR = (PFN_vkGetPipelineExecutableStatisticsKHR)load(context, "vkGetPipelineExecutableStatisticsKHR"); +#endif /* defined(VK_KHR_pipeline_executable_properties) */ +#if defined(VK_KHR_present_wait) + vkWaitForPresentKHR = (PFN_vkWaitForPresentKHR)load(context, "vkWaitForPresentKHR"); +#endif /* defined(VK_KHR_present_wait) */ +#if defined(VK_KHR_push_descriptor) + vkCmdPushDescriptorSetKHR = (PFN_vkCmdPushDescriptorSetKHR)load(context, "vkCmdPushDescriptorSetKHR"); +#endif /* defined(VK_KHR_push_descriptor) */ +#if defined(VK_KHR_ray_tracing_maintenance1) && defined(VK_KHR_ray_tracing_pipeline) + vkCmdTraceRaysIndirect2KHR = (PFN_vkCmdTraceRaysIndirect2KHR)load(context, "vkCmdTraceRaysIndirect2KHR"); +#endif /* defined(VK_KHR_ray_tracing_maintenance1) && defined(VK_KHR_ray_tracing_pipeline) */ +#if defined(VK_KHR_ray_tracing_pipeline) + vkCmdSetRayTracingPipelineStackSizeKHR = (PFN_vkCmdSetRayTracingPipelineStackSizeKHR)load(context, "vkCmdSetRayTracingPipelineStackSizeKHR"); + vkCmdTraceRaysIndirectKHR = (PFN_vkCmdTraceRaysIndirectKHR)load(context, "vkCmdTraceRaysIndirectKHR"); + vkCmdTraceRaysKHR = (PFN_vkCmdTraceRaysKHR)load(context, "vkCmdTraceRaysKHR"); + vkCreateRayTracingPipelinesKHR = (PFN_vkCreateRayTracingPipelinesKHR)load(context, "vkCreateRayTracingPipelinesKHR"); + vkGetRayTracingCaptureReplayShaderGroupHandlesKHR = (PFN_vkGetRayTracingCaptureReplayShaderGroupHandlesKHR)load(context, "vkGetRayTracingCaptureReplayShaderGroupHandlesKHR"); + vkGetRayTracingShaderGroupHandlesKHR = (PFN_vkGetRayTracingShaderGroupHandlesKHR)load(context, "vkGetRayTracingShaderGroupHandlesKHR"); + vkGetRayTracingShaderGroupStackSizeKHR = (PFN_vkGetRayTracingShaderGroupStackSizeKHR)load(context, "vkGetRayTracingShaderGroupStackSizeKHR"); +#endif /* defined(VK_KHR_ray_tracing_pipeline) */ +#if defined(VK_KHR_sampler_ycbcr_conversion) + vkCreateSamplerYcbcrConversionKHR = (PFN_vkCreateSamplerYcbcrConversionKHR)load(context, "vkCreateSamplerYcbcrConversionKHR"); + vkDestroySamplerYcbcrConversionKHR = (PFN_vkDestroySamplerYcbcrConversionKHR)load(context, "vkDestroySamplerYcbcrConversionKHR"); +#endif /* defined(VK_KHR_sampler_ycbcr_conversion) */ +#if defined(VK_KHR_shared_presentable_image) + vkGetSwapchainStatusKHR = (PFN_vkGetSwapchainStatusKHR)load(context, "vkGetSwapchainStatusKHR"); +#endif /* defined(VK_KHR_shared_presentable_image) */ +#if defined(VK_KHR_swapchain) + vkAcquireNextImageKHR = (PFN_vkAcquireNextImageKHR)load(context, "vkAcquireNextImageKHR"); + vkCreateSwapchainKHR = (PFN_vkCreateSwapchainKHR)load(context, "vkCreateSwapchainKHR"); + vkDestroySwapchainKHR = (PFN_vkDestroySwapchainKHR)load(context, "vkDestroySwapchainKHR"); + vkGetSwapchainImagesKHR = (PFN_vkGetSwapchainImagesKHR)load(context, "vkGetSwapchainImagesKHR"); + vkQueuePresentKHR = (PFN_vkQueuePresentKHR)load(context, "vkQueuePresentKHR"); +#endif /* defined(VK_KHR_swapchain) */ +#if defined(VK_KHR_synchronization2) + vkCmdPipelineBarrier2KHR = (PFN_vkCmdPipelineBarrier2KHR)load(context, "vkCmdPipelineBarrier2KHR"); + vkCmdResetEvent2KHR = (PFN_vkCmdResetEvent2KHR)load(context, "vkCmdResetEvent2KHR"); + vkCmdSetEvent2KHR = (PFN_vkCmdSetEvent2KHR)load(context, "vkCmdSetEvent2KHR"); + vkCmdWaitEvents2KHR = (PFN_vkCmdWaitEvents2KHR)load(context, "vkCmdWaitEvents2KHR"); + vkCmdWriteTimestamp2KHR = (PFN_vkCmdWriteTimestamp2KHR)load(context, "vkCmdWriteTimestamp2KHR"); + vkQueueSubmit2KHR = (PFN_vkQueueSubmit2KHR)load(context, "vkQueueSubmit2KHR"); +#endif /* defined(VK_KHR_synchronization2) */ +#if defined(VK_KHR_timeline_semaphore) + vkGetSemaphoreCounterValueKHR = (PFN_vkGetSemaphoreCounterValueKHR)load(context, "vkGetSemaphoreCounterValueKHR"); + vkSignalSemaphoreKHR = (PFN_vkSignalSemaphoreKHR)load(context, "vkSignalSemaphoreKHR"); + vkWaitSemaphoresKHR = (PFN_vkWaitSemaphoresKHR)load(context, "vkWaitSemaphoresKHR"); +#endif /* defined(VK_KHR_timeline_semaphore) */ +#if defined(VK_KHR_video_decode_queue) + vkCmdDecodeVideoKHR = (PFN_vkCmdDecodeVideoKHR)load(context, "vkCmdDecodeVideoKHR"); +#endif /* defined(VK_KHR_video_decode_queue) */ +#if defined(VK_KHR_video_encode_queue) + vkCmdEncodeVideoKHR = (PFN_vkCmdEncodeVideoKHR)load(context, "vkCmdEncodeVideoKHR"); + vkGetEncodedVideoSessionParametersKHR = (PFN_vkGetEncodedVideoSessionParametersKHR)load(context, "vkGetEncodedVideoSessionParametersKHR"); +#endif /* defined(VK_KHR_video_encode_queue) */ +#if defined(VK_KHR_video_queue) + vkBindVideoSessionMemoryKHR = (PFN_vkBindVideoSessionMemoryKHR)load(context, "vkBindVideoSessionMemoryKHR"); + vkCmdBeginVideoCodingKHR = (PFN_vkCmdBeginVideoCodingKHR)load(context, "vkCmdBeginVideoCodingKHR"); + vkCmdControlVideoCodingKHR = (PFN_vkCmdControlVideoCodingKHR)load(context, "vkCmdControlVideoCodingKHR"); + vkCmdEndVideoCodingKHR = (PFN_vkCmdEndVideoCodingKHR)load(context, "vkCmdEndVideoCodingKHR"); + vkCreateVideoSessionKHR = (PFN_vkCreateVideoSessionKHR)load(context, "vkCreateVideoSessionKHR"); + vkCreateVideoSessionParametersKHR = (PFN_vkCreateVideoSessionParametersKHR)load(context, "vkCreateVideoSessionParametersKHR"); + vkDestroyVideoSessionKHR = (PFN_vkDestroyVideoSessionKHR)load(context, "vkDestroyVideoSessionKHR"); + vkDestroyVideoSessionParametersKHR = (PFN_vkDestroyVideoSessionParametersKHR)load(context, "vkDestroyVideoSessionParametersKHR"); + vkGetVideoSessionMemoryRequirementsKHR = (PFN_vkGetVideoSessionMemoryRequirementsKHR)load(context, "vkGetVideoSessionMemoryRequirementsKHR"); + vkUpdateVideoSessionParametersKHR = (PFN_vkUpdateVideoSessionParametersKHR)load(context, "vkUpdateVideoSessionParametersKHR"); +#endif /* defined(VK_KHR_video_queue) */ +#if defined(VK_NVX_binary_import) + vkCmdCuLaunchKernelNVX = (PFN_vkCmdCuLaunchKernelNVX)load(context, "vkCmdCuLaunchKernelNVX"); + vkCreateCuFunctionNVX = (PFN_vkCreateCuFunctionNVX)load(context, "vkCreateCuFunctionNVX"); + vkCreateCuModuleNVX = (PFN_vkCreateCuModuleNVX)load(context, "vkCreateCuModuleNVX"); + vkDestroyCuFunctionNVX = (PFN_vkDestroyCuFunctionNVX)load(context, "vkDestroyCuFunctionNVX"); + vkDestroyCuModuleNVX = (PFN_vkDestroyCuModuleNVX)load(context, "vkDestroyCuModuleNVX"); +#endif /* defined(VK_NVX_binary_import) */ +#if defined(VK_NVX_image_view_handle) + vkGetImageViewHandleNVX = (PFN_vkGetImageViewHandleNVX)load(context, "vkGetImageViewHandleNVX"); +#endif /* defined(VK_NVX_image_view_handle) */ +#if defined(VK_NVX_image_view_handle) && VK_NVX_IMAGE_VIEW_HANDLE_SPEC_VERSION >= 3 + vkGetImageViewHandle64NVX = (PFN_vkGetImageViewHandle64NVX)load(context, "vkGetImageViewHandle64NVX"); +#endif /* defined(VK_NVX_image_view_handle) && VK_NVX_IMAGE_VIEW_HANDLE_SPEC_VERSION >= 3 */ +#if defined(VK_NVX_image_view_handle) && VK_NVX_IMAGE_VIEW_HANDLE_SPEC_VERSION >= 2 + vkGetImageViewAddressNVX = (PFN_vkGetImageViewAddressNVX)load(context, "vkGetImageViewAddressNVX"); +#endif /* defined(VK_NVX_image_view_handle) && VK_NVX_IMAGE_VIEW_HANDLE_SPEC_VERSION >= 2 */ +#if defined(VK_NV_clip_space_w_scaling) + vkCmdSetViewportWScalingNV = (PFN_vkCmdSetViewportWScalingNV)load(context, "vkCmdSetViewportWScalingNV"); +#endif /* defined(VK_NV_clip_space_w_scaling) */ +#if defined(VK_NV_copy_memory_indirect) + vkCmdCopyMemoryIndirectNV = (PFN_vkCmdCopyMemoryIndirectNV)load(context, "vkCmdCopyMemoryIndirectNV"); + vkCmdCopyMemoryToImageIndirectNV = (PFN_vkCmdCopyMemoryToImageIndirectNV)load(context, "vkCmdCopyMemoryToImageIndirectNV"); +#endif /* defined(VK_NV_copy_memory_indirect) */ +#if defined(VK_NV_cuda_kernel_launch) + vkCmdCudaLaunchKernelNV = (PFN_vkCmdCudaLaunchKernelNV)load(context, "vkCmdCudaLaunchKernelNV"); + vkCreateCudaFunctionNV = (PFN_vkCreateCudaFunctionNV)load(context, "vkCreateCudaFunctionNV"); + vkCreateCudaModuleNV = (PFN_vkCreateCudaModuleNV)load(context, "vkCreateCudaModuleNV"); + vkDestroyCudaFunctionNV = (PFN_vkDestroyCudaFunctionNV)load(context, "vkDestroyCudaFunctionNV"); + vkDestroyCudaModuleNV = (PFN_vkDestroyCudaModuleNV)load(context, "vkDestroyCudaModuleNV"); + vkGetCudaModuleCacheNV = (PFN_vkGetCudaModuleCacheNV)load(context, "vkGetCudaModuleCacheNV"); +#endif /* defined(VK_NV_cuda_kernel_launch) */ +#if defined(VK_NV_device_diagnostic_checkpoints) + vkCmdSetCheckpointNV = (PFN_vkCmdSetCheckpointNV)load(context, "vkCmdSetCheckpointNV"); + vkGetQueueCheckpointDataNV = (PFN_vkGetQueueCheckpointDataNV)load(context, "vkGetQueueCheckpointDataNV"); +#endif /* defined(VK_NV_device_diagnostic_checkpoints) */ +#if defined(VK_NV_device_diagnostic_checkpoints) && (defined(VK_VERSION_1_3) || defined(VK_KHR_synchronization2)) + vkGetQueueCheckpointData2NV = (PFN_vkGetQueueCheckpointData2NV)load(context, "vkGetQueueCheckpointData2NV"); +#endif /* defined(VK_NV_device_diagnostic_checkpoints) && (defined(VK_VERSION_1_3) || defined(VK_KHR_synchronization2)) */ +#if defined(VK_NV_device_generated_commands) + vkCmdBindPipelineShaderGroupNV = (PFN_vkCmdBindPipelineShaderGroupNV)load(context, "vkCmdBindPipelineShaderGroupNV"); + vkCmdExecuteGeneratedCommandsNV = (PFN_vkCmdExecuteGeneratedCommandsNV)load(context, "vkCmdExecuteGeneratedCommandsNV"); + vkCmdPreprocessGeneratedCommandsNV = (PFN_vkCmdPreprocessGeneratedCommandsNV)load(context, "vkCmdPreprocessGeneratedCommandsNV"); + vkCreateIndirectCommandsLayoutNV = (PFN_vkCreateIndirectCommandsLayoutNV)load(context, "vkCreateIndirectCommandsLayoutNV"); + vkDestroyIndirectCommandsLayoutNV = (PFN_vkDestroyIndirectCommandsLayoutNV)load(context, "vkDestroyIndirectCommandsLayoutNV"); + vkGetGeneratedCommandsMemoryRequirementsNV = (PFN_vkGetGeneratedCommandsMemoryRequirementsNV)load(context, "vkGetGeneratedCommandsMemoryRequirementsNV"); +#endif /* defined(VK_NV_device_generated_commands) */ +#if defined(VK_NV_device_generated_commands_compute) + vkCmdUpdatePipelineIndirectBufferNV = (PFN_vkCmdUpdatePipelineIndirectBufferNV)load(context, "vkCmdUpdatePipelineIndirectBufferNV"); + vkGetPipelineIndirectDeviceAddressNV = (PFN_vkGetPipelineIndirectDeviceAddressNV)load(context, "vkGetPipelineIndirectDeviceAddressNV"); + vkGetPipelineIndirectMemoryRequirementsNV = (PFN_vkGetPipelineIndirectMemoryRequirementsNV)load(context, "vkGetPipelineIndirectMemoryRequirementsNV"); +#endif /* defined(VK_NV_device_generated_commands_compute) */ +#if defined(VK_NV_external_memory_rdma) + vkGetMemoryRemoteAddressNV = (PFN_vkGetMemoryRemoteAddressNV)load(context, "vkGetMemoryRemoteAddressNV"); +#endif /* defined(VK_NV_external_memory_rdma) */ +#if defined(VK_NV_external_memory_win32) + vkGetMemoryWin32HandleNV = (PFN_vkGetMemoryWin32HandleNV)load(context, "vkGetMemoryWin32HandleNV"); +#endif /* defined(VK_NV_external_memory_win32) */ +#if defined(VK_NV_fragment_shading_rate_enums) + vkCmdSetFragmentShadingRateEnumNV = (PFN_vkCmdSetFragmentShadingRateEnumNV)load(context, "vkCmdSetFragmentShadingRateEnumNV"); +#endif /* defined(VK_NV_fragment_shading_rate_enums) */ +#if defined(VK_NV_low_latency2) + vkGetLatencyTimingsNV = (PFN_vkGetLatencyTimingsNV)load(context, "vkGetLatencyTimingsNV"); + vkLatencySleepNV = (PFN_vkLatencySleepNV)load(context, "vkLatencySleepNV"); + vkQueueNotifyOutOfBandNV = (PFN_vkQueueNotifyOutOfBandNV)load(context, "vkQueueNotifyOutOfBandNV"); + vkSetLatencyMarkerNV = (PFN_vkSetLatencyMarkerNV)load(context, "vkSetLatencyMarkerNV"); + vkSetLatencySleepModeNV = (PFN_vkSetLatencySleepModeNV)load(context, "vkSetLatencySleepModeNV"); +#endif /* defined(VK_NV_low_latency2) */ +#if defined(VK_NV_memory_decompression) + vkCmdDecompressMemoryIndirectCountNV = (PFN_vkCmdDecompressMemoryIndirectCountNV)load(context, "vkCmdDecompressMemoryIndirectCountNV"); + vkCmdDecompressMemoryNV = (PFN_vkCmdDecompressMemoryNV)load(context, "vkCmdDecompressMemoryNV"); +#endif /* defined(VK_NV_memory_decompression) */ +#if defined(VK_NV_mesh_shader) + vkCmdDrawMeshTasksIndirectNV = (PFN_vkCmdDrawMeshTasksIndirectNV)load(context, "vkCmdDrawMeshTasksIndirectNV"); + vkCmdDrawMeshTasksNV = (PFN_vkCmdDrawMeshTasksNV)load(context, "vkCmdDrawMeshTasksNV"); +#endif /* defined(VK_NV_mesh_shader) */ +#if defined(VK_NV_mesh_shader) && (defined(VK_KHR_draw_indirect_count) || defined(VK_VERSION_1_2)) + vkCmdDrawMeshTasksIndirectCountNV = (PFN_vkCmdDrawMeshTasksIndirectCountNV)load(context, "vkCmdDrawMeshTasksIndirectCountNV"); +#endif /* defined(VK_NV_mesh_shader) && (defined(VK_KHR_draw_indirect_count) || defined(VK_VERSION_1_2)) */ +#if defined(VK_NV_optical_flow) + vkBindOpticalFlowSessionImageNV = (PFN_vkBindOpticalFlowSessionImageNV)load(context, "vkBindOpticalFlowSessionImageNV"); + vkCmdOpticalFlowExecuteNV = (PFN_vkCmdOpticalFlowExecuteNV)load(context, "vkCmdOpticalFlowExecuteNV"); + vkCreateOpticalFlowSessionNV = (PFN_vkCreateOpticalFlowSessionNV)load(context, "vkCreateOpticalFlowSessionNV"); + vkDestroyOpticalFlowSessionNV = (PFN_vkDestroyOpticalFlowSessionNV)load(context, "vkDestroyOpticalFlowSessionNV"); +#endif /* defined(VK_NV_optical_flow) */ +#if defined(VK_NV_ray_tracing) + vkBindAccelerationStructureMemoryNV = (PFN_vkBindAccelerationStructureMemoryNV)load(context, "vkBindAccelerationStructureMemoryNV"); + vkCmdBuildAccelerationStructureNV = (PFN_vkCmdBuildAccelerationStructureNV)load(context, "vkCmdBuildAccelerationStructureNV"); + vkCmdCopyAccelerationStructureNV = (PFN_vkCmdCopyAccelerationStructureNV)load(context, "vkCmdCopyAccelerationStructureNV"); + vkCmdTraceRaysNV = (PFN_vkCmdTraceRaysNV)load(context, "vkCmdTraceRaysNV"); + vkCmdWriteAccelerationStructuresPropertiesNV = (PFN_vkCmdWriteAccelerationStructuresPropertiesNV)load(context, "vkCmdWriteAccelerationStructuresPropertiesNV"); + vkCompileDeferredNV = (PFN_vkCompileDeferredNV)load(context, "vkCompileDeferredNV"); + vkCreateAccelerationStructureNV = (PFN_vkCreateAccelerationStructureNV)load(context, "vkCreateAccelerationStructureNV"); + vkCreateRayTracingPipelinesNV = (PFN_vkCreateRayTracingPipelinesNV)load(context, "vkCreateRayTracingPipelinesNV"); + vkDestroyAccelerationStructureNV = (PFN_vkDestroyAccelerationStructureNV)load(context, "vkDestroyAccelerationStructureNV"); + vkGetAccelerationStructureHandleNV = (PFN_vkGetAccelerationStructureHandleNV)load(context, "vkGetAccelerationStructureHandleNV"); + vkGetAccelerationStructureMemoryRequirementsNV = (PFN_vkGetAccelerationStructureMemoryRequirementsNV)load(context, "vkGetAccelerationStructureMemoryRequirementsNV"); + vkGetRayTracingShaderGroupHandlesNV = (PFN_vkGetRayTracingShaderGroupHandlesNV)load(context, "vkGetRayTracingShaderGroupHandlesNV"); +#endif /* defined(VK_NV_ray_tracing) */ +#if defined(VK_NV_scissor_exclusive) && VK_NV_SCISSOR_EXCLUSIVE_SPEC_VERSION >= 2 + vkCmdSetExclusiveScissorEnableNV = (PFN_vkCmdSetExclusiveScissorEnableNV)load(context, "vkCmdSetExclusiveScissorEnableNV"); +#endif /* defined(VK_NV_scissor_exclusive) && VK_NV_SCISSOR_EXCLUSIVE_SPEC_VERSION >= 2 */ +#if defined(VK_NV_scissor_exclusive) + vkCmdSetExclusiveScissorNV = (PFN_vkCmdSetExclusiveScissorNV)load(context, "vkCmdSetExclusiveScissorNV"); +#endif /* defined(VK_NV_scissor_exclusive) */ +#if defined(VK_NV_shading_rate_image) + vkCmdBindShadingRateImageNV = (PFN_vkCmdBindShadingRateImageNV)load(context, "vkCmdBindShadingRateImageNV"); + vkCmdSetCoarseSampleOrderNV = (PFN_vkCmdSetCoarseSampleOrderNV)load(context, "vkCmdSetCoarseSampleOrderNV"); + vkCmdSetViewportShadingRatePaletteNV = (PFN_vkCmdSetViewportShadingRatePaletteNV)load(context, "vkCmdSetViewportShadingRatePaletteNV"); +#endif /* defined(VK_NV_shading_rate_image) */ +#if defined(VK_QCOM_tile_properties) + vkGetDynamicRenderingTilePropertiesQCOM = (PFN_vkGetDynamicRenderingTilePropertiesQCOM)load(context, "vkGetDynamicRenderingTilePropertiesQCOM"); + vkGetFramebufferTilePropertiesQCOM = (PFN_vkGetFramebufferTilePropertiesQCOM)load(context, "vkGetFramebufferTilePropertiesQCOM"); +#endif /* defined(VK_QCOM_tile_properties) */ +#if defined(VK_QNX_external_memory_screen_buffer) + vkGetScreenBufferPropertiesQNX = (PFN_vkGetScreenBufferPropertiesQNX)load(context, "vkGetScreenBufferPropertiesQNX"); +#endif /* defined(VK_QNX_external_memory_screen_buffer) */ +#if defined(VK_VALVE_descriptor_set_host_mapping) + vkGetDescriptorSetHostMappingVALVE = (PFN_vkGetDescriptorSetHostMappingVALVE)load(context, "vkGetDescriptorSetHostMappingVALVE"); + vkGetDescriptorSetLayoutHostMappingInfoVALVE = (PFN_vkGetDescriptorSetLayoutHostMappingInfoVALVE)load(context, "vkGetDescriptorSetLayoutHostMappingInfoVALVE"); +#endif /* defined(VK_VALVE_descriptor_set_host_mapping) */ +#if (defined(VK_EXT_depth_clamp_control)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_depth_clamp_control)) + vkCmdSetDepthClampRangeEXT = (PFN_vkCmdSetDepthClampRangeEXT)load(context, "vkCmdSetDepthClampRangeEXT"); +#endif /* (defined(VK_EXT_depth_clamp_control)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_depth_clamp_control)) */ +#if (defined(VK_EXT_extended_dynamic_state)) || (defined(VK_EXT_shader_object)) + vkCmdBindVertexBuffers2EXT = (PFN_vkCmdBindVertexBuffers2EXT)load(context, "vkCmdBindVertexBuffers2EXT"); + vkCmdSetCullModeEXT = (PFN_vkCmdSetCullModeEXT)load(context, "vkCmdSetCullModeEXT"); + vkCmdSetDepthBoundsTestEnableEXT = (PFN_vkCmdSetDepthBoundsTestEnableEXT)load(context, "vkCmdSetDepthBoundsTestEnableEXT"); + vkCmdSetDepthCompareOpEXT = (PFN_vkCmdSetDepthCompareOpEXT)load(context, "vkCmdSetDepthCompareOpEXT"); + vkCmdSetDepthTestEnableEXT = (PFN_vkCmdSetDepthTestEnableEXT)load(context, "vkCmdSetDepthTestEnableEXT"); + vkCmdSetDepthWriteEnableEXT = (PFN_vkCmdSetDepthWriteEnableEXT)load(context, "vkCmdSetDepthWriteEnableEXT"); + vkCmdSetFrontFaceEXT = (PFN_vkCmdSetFrontFaceEXT)load(context, "vkCmdSetFrontFaceEXT"); + vkCmdSetPrimitiveTopologyEXT = (PFN_vkCmdSetPrimitiveTopologyEXT)load(context, "vkCmdSetPrimitiveTopologyEXT"); + vkCmdSetScissorWithCountEXT = (PFN_vkCmdSetScissorWithCountEXT)load(context, "vkCmdSetScissorWithCountEXT"); + vkCmdSetStencilOpEXT = (PFN_vkCmdSetStencilOpEXT)load(context, "vkCmdSetStencilOpEXT"); + vkCmdSetStencilTestEnableEXT = (PFN_vkCmdSetStencilTestEnableEXT)load(context, "vkCmdSetStencilTestEnableEXT"); + vkCmdSetViewportWithCountEXT = (PFN_vkCmdSetViewportWithCountEXT)load(context, "vkCmdSetViewportWithCountEXT"); +#endif /* (defined(VK_EXT_extended_dynamic_state)) || (defined(VK_EXT_shader_object)) */ +#if (defined(VK_EXT_extended_dynamic_state2)) || (defined(VK_EXT_shader_object)) + vkCmdSetDepthBiasEnableEXT = (PFN_vkCmdSetDepthBiasEnableEXT)load(context, "vkCmdSetDepthBiasEnableEXT"); + vkCmdSetLogicOpEXT = (PFN_vkCmdSetLogicOpEXT)load(context, "vkCmdSetLogicOpEXT"); + vkCmdSetPatchControlPointsEXT = (PFN_vkCmdSetPatchControlPointsEXT)load(context, "vkCmdSetPatchControlPointsEXT"); + vkCmdSetPrimitiveRestartEnableEXT = (PFN_vkCmdSetPrimitiveRestartEnableEXT)load(context, "vkCmdSetPrimitiveRestartEnableEXT"); + vkCmdSetRasterizerDiscardEnableEXT = (PFN_vkCmdSetRasterizerDiscardEnableEXT)load(context, "vkCmdSetRasterizerDiscardEnableEXT"); +#endif /* (defined(VK_EXT_extended_dynamic_state2)) || (defined(VK_EXT_shader_object)) */ +#if (defined(VK_EXT_extended_dynamic_state3)) || (defined(VK_EXT_shader_object)) + vkCmdSetAlphaToCoverageEnableEXT = (PFN_vkCmdSetAlphaToCoverageEnableEXT)load(context, "vkCmdSetAlphaToCoverageEnableEXT"); + vkCmdSetAlphaToOneEnableEXT = (PFN_vkCmdSetAlphaToOneEnableEXT)load(context, "vkCmdSetAlphaToOneEnableEXT"); + vkCmdSetColorBlendEnableEXT = (PFN_vkCmdSetColorBlendEnableEXT)load(context, "vkCmdSetColorBlendEnableEXT"); + vkCmdSetColorBlendEquationEXT = (PFN_vkCmdSetColorBlendEquationEXT)load(context, "vkCmdSetColorBlendEquationEXT"); + vkCmdSetColorWriteMaskEXT = (PFN_vkCmdSetColorWriteMaskEXT)load(context, "vkCmdSetColorWriteMaskEXT"); + vkCmdSetDepthClampEnableEXT = (PFN_vkCmdSetDepthClampEnableEXT)load(context, "vkCmdSetDepthClampEnableEXT"); + vkCmdSetLogicOpEnableEXT = (PFN_vkCmdSetLogicOpEnableEXT)load(context, "vkCmdSetLogicOpEnableEXT"); + vkCmdSetPolygonModeEXT = (PFN_vkCmdSetPolygonModeEXT)load(context, "vkCmdSetPolygonModeEXT"); + vkCmdSetRasterizationSamplesEXT = (PFN_vkCmdSetRasterizationSamplesEXT)load(context, "vkCmdSetRasterizationSamplesEXT"); + vkCmdSetSampleMaskEXT = (PFN_vkCmdSetSampleMaskEXT)load(context, "vkCmdSetSampleMaskEXT"); +#endif /* (defined(VK_EXT_extended_dynamic_state3)) || (defined(VK_EXT_shader_object)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && (defined(VK_KHR_maintenance2) || defined(VK_VERSION_1_1))) || (defined(VK_EXT_shader_object)) + vkCmdSetTessellationDomainOriginEXT = (PFN_vkCmdSetTessellationDomainOriginEXT)load(context, "vkCmdSetTessellationDomainOriginEXT"); +#endif /* (defined(VK_EXT_extended_dynamic_state3) && (defined(VK_KHR_maintenance2) || defined(VK_VERSION_1_1))) || (defined(VK_EXT_shader_object)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_transform_feedback)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_transform_feedback)) + vkCmdSetRasterizationStreamEXT = (PFN_vkCmdSetRasterizationStreamEXT)load(context, "vkCmdSetRasterizationStreamEXT"); +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_transform_feedback)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_transform_feedback)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_conservative_rasterization)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_conservative_rasterization)) + vkCmdSetConservativeRasterizationModeEXT = (PFN_vkCmdSetConservativeRasterizationModeEXT)load(context, "vkCmdSetConservativeRasterizationModeEXT"); + vkCmdSetExtraPrimitiveOverestimationSizeEXT = (PFN_vkCmdSetExtraPrimitiveOverestimationSizeEXT)load(context, "vkCmdSetExtraPrimitiveOverestimationSizeEXT"); +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_conservative_rasterization)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_conservative_rasterization)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_depth_clip_enable)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_depth_clip_enable)) + vkCmdSetDepthClipEnableEXT = (PFN_vkCmdSetDepthClipEnableEXT)load(context, "vkCmdSetDepthClipEnableEXT"); +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_depth_clip_enable)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_depth_clip_enable)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_sample_locations)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_sample_locations)) + vkCmdSetSampleLocationsEnableEXT = (PFN_vkCmdSetSampleLocationsEnableEXT)load(context, "vkCmdSetSampleLocationsEnableEXT"); +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_sample_locations)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_sample_locations)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_blend_operation_advanced)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_blend_operation_advanced)) + vkCmdSetColorBlendAdvancedEXT = (PFN_vkCmdSetColorBlendAdvancedEXT)load(context, "vkCmdSetColorBlendAdvancedEXT"); +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_blend_operation_advanced)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_blend_operation_advanced)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_provoking_vertex)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_provoking_vertex)) + vkCmdSetProvokingVertexModeEXT = (PFN_vkCmdSetProvokingVertexModeEXT)load(context, "vkCmdSetProvokingVertexModeEXT"); +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_provoking_vertex)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_provoking_vertex)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_line_rasterization)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_line_rasterization)) + vkCmdSetLineRasterizationModeEXT = (PFN_vkCmdSetLineRasterizationModeEXT)load(context, "vkCmdSetLineRasterizationModeEXT"); + vkCmdSetLineStippleEnableEXT = (PFN_vkCmdSetLineStippleEnableEXT)load(context, "vkCmdSetLineStippleEnableEXT"); +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_line_rasterization)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_line_rasterization)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_depth_clip_control)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_depth_clip_control)) + vkCmdSetDepthClipNegativeOneToOneEXT = (PFN_vkCmdSetDepthClipNegativeOneToOneEXT)load(context, "vkCmdSetDepthClipNegativeOneToOneEXT"); +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_depth_clip_control)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_depth_clip_control)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_clip_space_w_scaling)) || (defined(VK_EXT_shader_object) && defined(VK_NV_clip_space_w_scaling)) + vkCmdSetViewportWScalingEnableNV = (PFN_vkCmdSetViewportWScalingEnableNV)load(context, "vkCmdSetViewportWScalingEnableNV"); +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_clip_space_w_scaling)) || (defined(VK_EXT_shader_object) && defined(VK_NV_clip_space_w_scaling)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_viewport_swizzle)) || (defined(VK_EXT_shader_object) && defined(VK_NV_viewport_swizzle)) + vkCmdSetViewportSwizzleNV = (PFN_vkCmdSetViewportSwizzleNV)load(context, "vkCmdSetViewportSwizzleNV"); +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_viewport_swizzle)) || (defined(VK_EXT_shader_object) && defined(VK_NV_viewport_swizzle)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_fragment_coverage_to_color)) || (defined(VK_EXT_shader_object) && defined(VK_NV_fragment_coverage_to_color)) + vkCmdSetCoverageToColorEnableNV = (PFN_vkCmdSetCoverageToColorEnableNV)load(context, "vkCmdSetCoverageToColorEnableNV"); + vkCmdSetCoverageToColorLocationNV = (PFN_vkCmdSetCoverageToColorLocationNV)load(context, "vkCmdSetCoverageToColorLocationNV"); +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_fragment_coverage_to_color)) || (defined(VK_EXT_shader_object) && defined(VK_NV_fragment_coverage_to_color)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_framebuffer_mixed_samples)) || (defined(VK_EXT_shader_object) && defined(VK_NV_framebuffer_mixed_samples)) + vkCmdSetCoverageModulationModeNV = (PFN_vkCmdSetCoverageModulationModeNV)load(context, "vkCmdSetCoverageModulationModeNV"); + vkCmdSetCoverageModulationTableEnableNV = (PFN_vkCmdSetCoverageModulationTableEnableNV)load(context, "vkCmdSetCoverageModulationTableEnableNV"); + vkCmdSetCoverageModulationTableNV = (PFN_vkCmdSetCoverageModulationTableNV)load(context, "vkCmdSetCoverageModulationTableNV"); +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_framebuffer_mixed_samples)) || (defined(VK_EXT_shader_object) && defined(VK_NV_framebuffer_mixed_samples)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_shading_rate_image)) || (defined(VK_EXT_shader_object) && defined(VK_NV_shading_rate_image)) + vkCmdSetShadingRateImageEnableNV = (PFN_vkCmdSetShadingRateImageEnableNV)load(context, "vkCmdSetShadingRateImageEnableNV"); +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_shading_rate_image)) || (defined(VK_EXT_shader_object) && defined(VK_NV_shading_rate_image)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_representative_fragment_test)) || (defined(VK_EXT_shader_object) && defined(VK_NV_representative_fragment_test)) + vkCmdSetRepresentativeFragmentTestEnableNV = (PFN_vkCmdSetRepresentativeFragmentTestEnableNV)load(context, "vkCmdSetRepresentativeFragmentTestEnableNV"); +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_representative_fragment_test)) || (defined(VK_EXT_shader_object) && defined(VK_NV_representative_fragment_test)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_coverage_reduction_mode)) || (defined(VK_EXT_shader_object) && defined(VK_NV_coverage_reduction_mode)) + vkCmdSetCoverageReductionModeNV = (PFN_vkCmdSetCoverageReductionModeNV)load(context, "vkCmdSetCoverageReductionModeNV"); +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_coverage_reduction_mode)) || (defined(VK_EXT_shader_object) && defined(VK_NV_coverage_reduction_mode)) */ +#if (defined(VK_EXT_host_image_copy)) || (defined(VK_EXT_image_compression_control)) + vkGetImageSubresourceLayout2EXT = (PFN_vkGetImageSubresourceLayout2EXT)load(context, "vkGetImageSubresourceLayout2EXT"); +#endif /* (defined(VK_EXT_host_image_copy)) || (defined(VK_EXT_image_compression_control)) */ +#if (defined(VK_EXT_shader_object)) || (defined(VK_EXT_vertex_input_dynamic_state)) + vkCmdSetVertexInputEXT = (PFN_vkCmdSetVertexInputEXT)load(context, "vkCmdSetVertexInputEXT"); +#endif /* (defined(VK_EXT_shader_object)) || (defined(VK_EXT_vertex_input_dynamic_state)) */ +#if (defined(VK_KHR_descriptor_update_template) && defined(VK_KHR_push_descriptor)) || (defined(VK_KHR_push_descriptor) && (defined(VK_VERSION_1_1) || defined(VK_KHR_descriptor_update_template))) + vkCmdPushDescriptorSetWithTemplateKHR = (PFN_vkCmdPushDescriptorSetWithTemplateKHR)load(context, "vkCmdPushDescriptorSetWithTemplateKHR"); +#endif /* (defined(VK_KHR_descriptor_update_template) && defined(VK_KHR_push_descriptor)) || (defined(VK_KHR_push_descriptor) && (defined(VK_VERSION_1_1) || defined(VK_KHR_descriptor_update_template))) */ +#if (defined(VK_KHR_device_group) && defined(VK_KHR_surface)) || (defined(VK_KHR_swapchain) && defined(VK_VERSION_1_1)) + vkGetDeviceGroupPresentCapabilitiesKHR = (PFN_vkGetDeviceGroupPresentCapabilitiesKHR)load(context, "vkGetDeviceGroupPresentCapabilitiesKHR"); + vkGetDeviceGroupSurfacePresentModesKHR = (PFN_vkGetDeviceGroupSurfacePresentModesKHR)load(context, "vkGetDeviceGroupSurfacePresentModesKHR"); +#endif /* (defined(VK_KHR_device_group) && defined(VK_KHR_surface)) || (defined(VK_KHR_swapchain) && defined(VK_VERSION_1_1)) */ +#if (defined(VK_KHR_device_group) && defined(VK_KHR_swapchain)) || (defined(VK_KHR_swapchain) && defined(VK_VERSION_1_1)) + vkAcquireNextImage2KHR = (PFN_vkAcquireNextImage2KHR)load(context, "vkAcquireNextImage2KHR"); +#endif /* (defined(VK_KHR_device_group) && defined(VK_KHR_swapchain)) || (defined(VK_KHR_swapchain) && defined(VK_VERSION_1_1)) */ + /* VOLK_GENERATE_LOAD_DEVICE */ +} + +static void volkGenLoadDeviceTable(struct VolkDeviceTable* table, void* context, PFN_vkVoidFunction (*load)(void*, const char*)) +{ + /* VOLK_GENERATE_LOAD_DEVICE_TABLE */ +#if defined(VK_VERSION_1_0) + table->vkAllocateCommandBuffers = (PFN_vkAllocateCommandBuffers)load(context, "vkAllocateCommandBuffers"); + table->vkAllocateDescriptorSets = (PFN_vkAllocateDescriptorSets)load(context, "vkAllocateDescriptorSets"); + table->vkAllocateMemory = (PFN_vkAllocateMemory)load(context, "vkAllocateMemory"); + table->vkBeginCommandBuffer = (PFN_vkBeginCommandBuffer)load(context, "vkBeginCommandBuffer"); + table->vkBindBufferMemory = (PFN_vkBindBufferMemory)load(context, "vkBindBufferMemory"); + table->vkBindImageMemory = (PFN_vkBindImageMemory)load(context, "vkBindImageMemory"); + table->vkCmdBeginQuery = (PFN_vkCmdBeginQuery)load(context, "vkCmdBeginQuery"); + table->vkCmdBeginRenderPass = (PFN_vkCmdBeginRenderPass)load(context, "vkCmdBeginRenderPass"); + table->vkCmdBindDescriptorSets = (PFN_vkCmdBindDescriptorSets)load(context, "vkCmdBindDescriptorSets"); + table->vkCmdBindIndexBuffer = (PFN_vkCmdBindIndexBuffer)load(context, "vkCmdBindIndexBuffer"); + table->vkCmdBindPipeline = (PFN_vkCmdBindPipeline)load(context, "vkCmdBindPipeline"); + table->vkCmdBindVertexBuffers = (PFN_vkCmdBindVertexBuffers)load(context, "vkCmdBindVertexBuffers"); + table->vkCmdBlitImage = (PFN_vkCmdBlitImage)load(context, "vkCmdBlitImage"); + table->vkCmdClearAttachments = (PFN_vkCmdClearAttachments)load(context, "vkCmdClearAttachments"); + table->vkCmdClearColorImage = (PFN_vkCmdClearColorImage)load(context, "vkCmdClearColorImage"); + table->vkCmdClearDepthStencilImage = (PFN_vkCmdClearDepthStencilImage)load(context, "vkCmdClearDepthStencilImage"); + table->vkCmdCopyBuffer = (PFN_vkCmdCopyBuffer)load(context, "vkCmdCopyBuffer"); + table->vkCmdCopyBufferToImage = (PFN_vkCmdCopyBufferToImage)load(context, "vkCmdCopyBufferToImage"); + table->vkCmdCopyImage = (PFN_vkCmdCopyImage)load(context, "vkCmdCopyImage"); + table->vkCmdCopyImageToBuffer = (PFN_vkCmdCopyImageToBuffer)load(context, "vkCmdCopyImageToBuffer"); + table->vkCmdCopyQueryPoolResults = (PFN_vkCmdCopyQueryPoolResults)load(context, "vkCmdCopyQueryPoolResults"); + table->vkCmdDispatch = (PFN_vkCmdDispatch)load(context, "vkCmdDispatch"); + table->vkCmdDispatchIndirect = (PFN_vkCmdDispatchIndirect)load(context, "vkCmdDispatchIndirect"); + table->vkCmdDraw = (PFN_vkCmdDraw)load(context, "vkCmdDraw"); + table->vkCmdDrawIndexed = (PFN_vkCmdDrawIndexed)load(context, "vkCmdDrawIndexed"); + table->vkCmdDrawIndexedIndirect = (PFN_vkCmdDrawIndexedIndirect)load(context, "vkCmdDrawIndexedIndirect"); + table->vkCmdDrawIndirect = (PFN_vkCmdDrawIndirect)load(context, "vkCmdDrawIndirect"); + table->vkCmdEndQuery = (PFN_vkCmdEndQuery)load(context, "vkCmdEndQuery"); + table->vkCmdEndRenderPass = (PFN_vkCmdEndRenderPass)load(context, "vkCmdEndRenderPass"); + table->vkCmdExecuteCommands = (PFN_vkCmdExecuteCommands)load(context, "vkCmdExecuteCommands"); + table->vkCmdFillBuffer = (PFN_vkCmdFillBuffer)load(context, "vkCmdFillBuffer"); + table->vkCmdNextSubpass = (PFN_vkCmdNextSubpass)load(context, "vkCmdNextSubpass"); + table->vkCmdPipelineBarrier = (PFN_vkCmdPipelineBarrier)load(context, "vkCmdPipelineBarrier"); + table->vkCmdPushConstants = (PFN_vkCmdPushConstants)load(context, "vkCmdPushConstants"); + table->vkCmdResetEvent = (PFN_vkCmdResetEvent)load(context, "vkCmdResetEvent"); + table->vkCmdResetQueryPool = (PFN_vkCmdResetQueryPool)load(context, "vkCmdResetQueryPool"); + table->vkCmdResolveImage = (PFN_vkCmdResolveImage)load(context, "vkCmdResolveImage"); + table->vkCmdSetBlendConstants = (PFN_vkCmdSetBlendConstants)load(context, "vkCmdSetBlendConstants"); + table->vkCmdSetDepthBias = (PFN_vkCmdSetDepthBias)load(context, "vkCmdSetDepthBias"); + table->vkCmdSetDepthBounds = (PFN_vkCmdSetDepthBounds)load(context, "vkCmdSetDepthBounds"); + table->vkCmdSetEvent = (PFN_vkCmdSetEvent)load(context, "vkCmdSetEvent"); + table->vkCmdSetLineWidth = (PFN_vkCmdSetLineWidth)load(context, "vkCmdSetLineWidth"); + table->vkCmdSetScissor = (PFN_vkCmdSetScissor)load(context, "vkCmdSetScissor"); + table->vkCmdSetStencilCompareMask = (PFN_vkCmdSetStencilCompareMask)load(context, "vkCmdSetStencilCompareMask"); + table->vkCmdSetStencilReference = (PFN_vkCmdSetStencilReference)load(context, "vkCmdSetStencilReference"); + table->vkCmdSetStencilWriteMask = (PFN_vkCmdSetStencilWriteMask)load(context, "vkCmdSetStencilWriteMask"); + table->vkCmdSetViewport = (PFN_vkCmdSetViewport)load(context, "vkCmdSetViewport"); + table->vkCmdUpdateBuffer = (PFN_vkCmdUpdateBuffer)load(context, "vkCmdUpdateBuffer"); + table->vkCmdWaitEvents = (PFN_vkCmdWaitEvents)load(context, "vkCmdWaitEvents"); + table->vkCmdWriteTimestamp = (PFN_vkCmdWriteTimestamp)load(context, "vkCmdWriteTimestamp"); + table->vkCreateBuffer = (PFN_vkCreateBuffer)load(context, "vkCreateBuffer"); + table->vkCreateBufferView = (PFN_vkCreateBufferView)load(context, "vkCreateBufferView"); + table->vkCreateCommandPool = (PFN_vkCreateCommandPool)load(context, "vkCreateCommandPool"); + table->vkCreateComputePipelines = (PFN_vkCreateComputePipelines)load(context, "vkCreateComputePipelines"); + table->vkCreateDescriptorPool = (PFN_vkCreateDescriptorPool)load(context, "vkCreateDescriptorPool"); + table->vkCreateDescriptorSetLayout = (PFN_vkCreateDescriptorSetLayout)load(context, "vkCreateDescriptorSetLayout"); + table->vkCreateEvent = (PFN_vkCreateEvent)load(context, "vkCreateEvent"); + table->vkCreateFence = (PFN_vkCreateFence)load(context, "vkCreateFence"); + table->vkCreateFramebuffer = (PFN_vkCreateFramebuffer)load(context, "vkCreateFramebuffer"); + table->vkCreateGraphicsPipelines = (PFN_vkCreateGraphicsPipelines)load(context, "vkCreateGraphicsPipelines"); + table->vkCreateImage = (PFN_vkCreateImage)load(context, "vkCreateImage"); + table->vkCreateImageView = (PFN_vkCreateImageView)load(context, "vkCreateImageView"); + table->vkCreatePipelineCache = (PFN_vkCreatePipelineCache)load(context, "vkCreatePipelineCache"); + table->vkCreatePipelineLayout = (PFN_vkCreatePipelineLayout)load(context, "vkCreatePipelineLayout"); + table->vkCreateQueryPool = (PFN_vkCreateQueryPool)load(context, "vkCreateQueryPool"); + table->vkCreateRenderPass = (PFN_vkCreateRenderPass)load(context, "vkCreateRenderPass"); + table->vkCreateSampler = (PFN_vkCreateSampler)load(context, "vkCreateSampler"); + table->vkCreateSemaphore = (PFN_vkCreateSemaphore)load(context, "vkCreateSemaphore"); + table->vkCreateShaderModule = (PFN_vkCreateShaderModule)load(context, "vkCreateShaderModule"); + table->vkDestroyBuffer = (PFN_vkDestroyBuffer)load(context, "vkDestroyBuffer"); + table->vkDestroyBufferView = (PFN_vkDestroyBufferView)load(context, "vkDestroyBufferView"); + table->vkDestroyCommandPool = (PFN_vkDestroyCommandPool)load(context, "vkDestroyCommandPool"); + table->vkDestroyDescriptorPool = (PFN_vkDestroyDescriptorPool)load(context, "vkDestroyDescriptorPool"); + table->vkDestroyDescriptorSetLayout = (PFN_vkDestroyDescriptorSetLayout)load(context, "vkDestroyDescriptorSetLayout"); + table->vkDestroyDevice = (PFN_vkDestroyDevice)load(context, "vkDestroyDevice"); + table->vkDestroyEvent = (PFN_vkDestroyEvent)load(context, "vkDestroyEvent"); + table->vkDestroyFence = (PFN_vkDestroyFence)load(context, "vkDestroyFence"); + table->vkDestroyFramebuffer = (PFN_vkDestroyFramebuffer)load(context, "vkDestroyFramebuffer"); + table->vkDestroyImage = (PFN_vkDestroyImage)load(context, "vkDestroyImage"); + table->vkDestroyImageView = (PFN_vkDestroyImageView)load(context, "vkDestroyImageView"); + table->vkDestroyPipeline = (PFN_vkDestroyPipeline)load(context, "vkDestroyPipeline"); + table->vkDestroyPipelineCache = (PFN_vkDestroyPipelineCache)load(context, "vkDestroyPipelineCache"); + table->vkDestroyPipelineLayout = (PFN_vkDestroyPipelineLayout)load(context, "vkDestroyPipelineLayout"); + table->vkDestroyQueryPool = (PFN_vkDestroyQueryPool)load(context, "vkDestroyQueryPool"); + table->vkDestroyRenderPass = (PFN_vkDestroyRenderPass)load(context, "vkDestroyRenderPass"); + table->vkDestroySampler = (PFN_vkDestroySampler)load(context, "vkDestroySampler"); + table->vkDestroySemaphore = (PFN_vkDestroySemaphore)load(context, "vkDestroySemaphore"); + table->vkDestroyShaderModule = (PFN_vkDestroyShaderModule)load(context, "vkDestroyShaderModule"); + table->vkDeviceWaitIdle = (PFN_vkDeviceWaitIdle)load(context, "vkDeviceWaitIdle"); + table->vkEndCommandBuffer = (PFN_vkEndCommandBuffer)load(context, "vkEndCommandBuffer"); + table->vkFlushMappedMemoryRanges = (PFN_vkFlushMappedMemoryRanges)load(context, "vkFlushMappedMemoryRanges"); + table->vkFreeCommandBuffers = (PFN_vkFreeCommandBuffers)load(context, "vkFreeCommandBuffers"); + table->vkFreeDescriptorSets = (PFN_vkFreeDescriptorSets)load(context, "vkFreeDescriptorSets"); + table->vkFreeMemory = (PFN_vkFreeMemory)load(context, "vkFreeMemory"); + table->vkGetBufferMemoryRequirements = (PFN_vkGetBufferMemoryRequirements)load(context, "vkGetBufferMemoryRequirements"); + table->vkGetDeviceMemoryCommitment = (PFN_vkGetDeviceMemoryCommitment)load(context, "vkGetDeviceMemoryCommitment"); + table->vkGetDeviceQueue = (PFN_vkGetDeviceQueue)load(context, "vkGetDeviceQueue"); + table->vkGetEventStatus = (PFN_vkGetEventStatus)load(context, "vkGetEventStatus"); + table->vkGetFenceStatus = (PFN_vkGetFenceStatus)load(context, "vkGetFenceStatus"); + table->vkGetImageMemoryRequirements = (PFN_vkGetImageMemoryRequirements)load(context, "vkGetImageMemoryRequirements"); + table->vkGetImageSparseMemoryRequirements = (PFN_vkGetImageSparseMemoryRequirements)load(context, "vkGetImageSparseMemoryRequirements"); + table->vkGetImageSubresourceLayout = (PFN_vkGetImageSubresourceLayout)load(context, "vkGetImageSubresourceLayout"); + table->vkGetPipelineCacheData = (PFN_vkGetPipelineCacheData)load(context, "vkGetPipelineCacheData"); + table->vkGetQueryPoolResults = (PFN_vkGetQueryPoolResults)load(context, "vkGetQueryPoolResults"); + table->vkGetRenderAreaGranularity = (PFN_vkGetRenderAreaGranularity)load(context, "vkGetRenderAreaGranularity"); + table->vkInvalidateMappedMemoryRanges = (PFN_vkInvalidateMappedMemoryRanges)load(context, "vkInvalidateMappedMemoryRanges"); + table->vkMapMemory = (PFN_vkMapMemory)load(context, "vkMapMemory"); + table->vkMergePipelineCaches = (PFN_vkMergePipelineCaches)load(context, "vkMergePipelineCaches"); + table->vkQueueBindSparse = (PFN_vkQueueBindSparse)load(context, "vkQueueBindSparse"); + table->vkQueueSubmit = (PFN_vkQueueSubmit)load(context, "vkQueueSubmit"); + table->vkQueueWaitIdle = (PFN_vkQueueWaitIdle)load(context, "vkQueueWaitIdle"); + table->vkResetCommandBuffer = (PFN_vkResetCommandBuffer)load(context, "vkResetCommandBuffer"); + table->vkResetCommandPool = (PFN_vkResetCommandPool)load(context, "vkResetCommandPool"); + table->vkResetDescriptorPool = (PFN_vkResetDescriptorPool)load(context, "vkResetDescriptorPool"); + table->vkResetEvent = (PFN_vkResetEvent)load(context, "vkResetEvent"); + table->vkResetFences = (PFN_vkResetFences)load(context, "vkResetFences"); + table->vkSetEvent = (PFN_vkSetEvent)load(context, "vkSetEvent"); + table->vkUnmapMemory = (PFN_vkUnmapMemory)load(context, "vkUnmapMemory"); + table->vkUpdateDescriptorSets = (PFN_vkUpdateDescriptorSets)load(context, "vkUpdateDescriptorSets"); + table->vkWaitForFences = (PFN_vkWaitForFences)load(context, "vkWaitForFences"); +#endif /* defined(VK_VERSION_1_0) */ +#if defined(VK_VERSION_1_1) + table->vkBindBufferMemory2 = (PFN_vkBindBufferMemory2)load(context, "vkBindBufferMemory2"); + table->vkBindImageMemory2 = (PFN_vkBindImageMemory2)load(context, "vkBindImageMemory2"); + table->vkCmdDispatchBase = (PFN_vkCmdDispatchBase)load(context, "vkCmdDispatchBase"); + table->vkCmdSetDeviceMask = (PFN_vkCmdSetDeviceMask)load(context, "vkCmdSetDeviceMask"); + table->vkCreateDescriptorUpdateTemplate = (PFN_vkCreateDescriptorUpdateTemplate)load(context, "vkCreateDescriptorUpdateTemplate"); + table->vkCreateSamplerYcbcrConversion = (PFN_vkCreateSamplerYcbcrConversion)load(context, "vkCreateSamplerYcbcrConversion"); + table->vkDestroyDescriptorUpdateTemplate = (PFN_vkDestroyDescriptorUpdateTemplate)load(context, "vkDestroyDescriptorUpdateTemplate"); + table->vkDestroySamplerYcbcrConversion = (PFN_vkDestroySamplerYcbcrConversion)load(context, "vkDestroySamplerYcbcrConversion"); + table->vkGetBufferMemoryRequirements2 = (PFN_vkGetBufferMemoryRequirements2)load(context, "vkGetBufferMemoryRequirements2"); + table->vkGetDescriptorSetLayoutSupport = (PFN_vkGetDescriptorSetLayoutSupport)load(context, "vkGetDescriptorSetLayoutSupport"); + table->vkGetDeviceGroupPeerMemoryFeatures = (PFN_vkGetDeviceGroupPeerMemoryFeatures)load(context, "vkGetDeviceGroupPeerMemoryFeatures"); + table->vkGetDeviceQueue2 = (PFN_vkGetDeviceQueue2)load(context, "vkGetDeviceQueue2"); + table->vkGetImageMemoryRequirements2 = (PFN_vkGetImageMemoryRequirements2)load(context, "vkGetImageMemoryRequirements2"); + table->vkGetImageSparseMemoryRequirements2 = (PFN_vkGetImageSparseMemoryRequirements2)load(context, "vkGetImageSparseMemoryRequirements2"); + table->vkTrimCommandPool = (PFN_vkTrimCommandPool)load(context, "vkTrimCommandPool"); + table->vkUpdateDescriptorSetWithTemplate = (PFN_vkUpdateDescriptorSetWithTemplate)load(context, "vkUpdateDescriptorSetWithTemplate"); +#endif /* defined(VK_VERSION_1_1) */ +#if defined(VK_VERSION_1_2) + table->vkCmdBeginRenderPass2 = (PFN_vkCmdBeginRenderPass2)load(context, "vkCmdBeginRenderPass2"); + table->vkCmdDrawIndexedIndirectCount = (PFN_vkCmdDrawIndexedIndirectCount)load(context, "vkCmdDrawIndexedIndirectCount"); + table->vkCmdDrawIndirectCount = (PFN_vkCmdDrawIndirectCount)load(context, "vkCmdDrawIndirectCount"); + table->vkCmdEndRenderPass2 = (PFN_vkCmdEndRenderPass2)load(context, "vkCmdEndRenderPass2"); + table->vkCmdNextSubpass2 = (PFN_vkCmdNextSubpass2)load(context, "vkCmdNextSubpass2"); + table->vkCreateRenderPass2 = (PFN_vkCreateRenderPass2)load(context, "vkCreateRenderPass2"); + table->vkGetBufferDeviceAddress = (PFN_vkGetBufferDeviceAddress)load(context, "vkGetBufferDeviceAddress"); + table->vkGetBufferOpaqueCaptureAddress = (PFN_vkGetBufferOpaqueCaptureAddress)load(context, "vkGetBufferOpaqueCaptureAddress"); + table->vkGetDeviceMemoryOpaqueCaptureAddress = (PFN_vkGetDeviceMemoryOpaqueCaptureAddress)load(context, "vkGetDeviceMemoryOpaqueCaptureAddress"); + table->vkGetSemaphoreCounterValue = (PFN_vkGetSemaphoreCounterValue)load(context, "vkGetSemaphoreCounterValue"); + table->vkResetQueryPool = (PFN_vkResetQueryPool)load(context, "vkResetQueryPool"); + table->vkSignalSemaphore = (PFN_vkSignalSemaphore)load(context, "vkSignalSemaphore"); + table->vkWaitSemaphores = (PFN_vkWaitSemaphores)load(context, "vkWaitSemaphores"); +#endif /* defined(VK_VERSION_1_2) */ +#if defined(VK_VERSION_1_3) + table->vkCmdBeginRendering = (PFN_vkCmdBeginRendering)load(context, "vkCmdBeginRendering"); + table->vkCmdBindVertexBuffers2 = (PFN_vkCmdBindVertexBuffers2)load(context, "vkCmdBindVertexBuffers2"); + table->vkCmdBlitImage2 = (PFN_vkCmdBlitImage2)load(context, "vkCmdBlitImage2"); + table->vkCmdCopyBuffer2 = (PFN_vkCmdCopyBuffer2)load(context, "vkCmdCopyBuffer2"); + table->vkCmdCopyBufferToImage2 = (PFN_vkCmdCopyBufferToImage2)load(context, "vkCmdCopyBufferToImage2"); + table->vkCmdCopyImage2 = (PFN_vkCmdCopyImage2)load(context, "vkCmdCopyImage2"); + table->vkCmdCopyImageToBuffer2 = (PFN_vkCmdCopyImageToBuffer2)load(context, "vkCmdCopyImageToBuffer2"); + table->vkCmdEndRendering = (PFN_vkCmdEndRendering)load(context, "vkCmdEndRendering"); + table->vkCmdPipelineBarrier2 = (PFN_vkCmdPipelineBarrier2)load(context, "vkCmdPipelineBarrier2"); + table->vkCmdResetEvent2 = (PFN_vkCmdResetEvent2)load(context, "vkCmdResetEvent2"); + table->vkCmdResolveImage2 = (PFN_vkCmdResolveImage2)load(context, "vkCmdResolveImage2"); + table->vkCmdSetCullMode = (PFN_vkCmdSetCullMode)load(context, "vkCmdSetCullMode"); + table->vkCmdSetDepthBiasEnable = (PFN_vkCmdSetDepthBiasEnable)load(context, "vkCmdSetDepthBiasEnable"); + table->vkCmdSetDepthBoundsTestEnable = (PFN_vkCmdSetDepthBoundsTestEnable)load(context, "vkCmdSetDepthBoundsTestEnable"); + table->vkCmdSetDepthCompareOp = (PFN_vkCmdSetDepthCompareOp)load(context, "vkCmdSetDepthCompareOp"); + table->vkCmdSetDepthTestEnable = (PFN_vkCmdSetDepthTestEnable)load(context, "vkCmdSetDepthTestEnable"); + table->vkCmdSetDepthWriteEnable = (PFN_vkCmdSetDepthWriteEnable)load(context, "vkCmdSetDepthWriteEnable"); + table->vkCmdSetEvent2 = (PFN_vkCmdSetEvent2)load(context, "vkCmdSetEvent2"); + table->vkCmdSetFrontFace = (PFN_vkCmdSetFrontFace)load(context, "vkCmdSetFrontFace"); + table->vkCmdSetPrimitiveRestartEnable = (PFN_vkCmdSetPrimitiveRestartEnable)load(context, "vkCmdSetPrimitiveRestartEnable"); + table->vkCmdSetPrimitiveTopology = (PFN_vkCmdSetPrimitiveTopology)load(context, "vkCmdSetPrimitiveTopology"); + table->vkCmdSetRasterizerDiscardEnable = (PFN_vkCmdSetRasterizerDiscardEnable)load(context, "vkCmdSetRasterizerDiscardEnable"); + table->vkCmdSetScissorWithCount = (PFN_vkCmdSetScissorWithCount)load(context, "vkCmdSetScissorWithCount"); + table->vkCmdSetStencilOp = (PFN_vkCmdSetStencilOp)load(context, "vkCmdSetStencilOp"); + table->vkCmdSetStencilTestEnable = (PFN_vkCmdSetStencilTestEnable)load(context, "vkCmdSetStencilTestEnable"); + table->vkCmdSetViewportWithCount = (PFN_vkCmdSetViewportWithCount)load(context, "vkCmdSetViewportWithCount"); + table->vkCmdWaitEvents2 = (PFN_vkCmdWaitEvents2)load(context, "vkCmdWaitEvents2"); + table->vkCmdWriteTimestamp2 = (PFN_vkCmdWriteTimestamp2)load(context, "vkCmdWriteTimestamp2"); + table->vkCreatePrivateDataSlot = (PFN_vkCreatePrivateDataSlot)load(context, "vkCreatePrivateDataSlot"); + table->vkDestroyPrivateDataSlot = (PFN_vkDestroyPrivateDataSlot)load(context, "vkDestroyPrivateDataSlot"); + table->vkGetDeviceBufferMemoryRequirements = (PFN_vkGetDeviceBufferMemoryRequirements)load(context, "vkGetDeviceBufferMemoryRequirements"); + table->vkGetDeviceImageMemoryRequirements = (PFN_vkGetDeviceImageMemoryRequirements)load(context, "vkGetDeviceImageMemoryRequirements"); + table->vkGetDeviceImageSparseMemoryRequirements = (PFN_vkGetDeviceImageSparseMemoryRequirements)load(context, "vkGetDeviceImageSparseMemoryRequirements"); + table->vkGetPrivateData = (PFN_vkGetPrivateData)load(context, "vkGetPrivateData"); + table->vkQueueSubmit2 = (PFN_vkQueueSubmit2)load(context, "vkQueueSubmit2"); + table->vkSetPrivateData = (PFN_vkSetPrivateData)load(context, "vkSetPrivateData"); +#endif /* defined(VK_VERSION_1_3) */ +#if defined(VK_VERSION_1_4) + table->vkCmdBindDescriptorSets2 = (PFN_vkCmdBindDescriptorSets2)load(context, "vkCmdBindDescriptorSets2"); + table->vkCmdBindIndexBuffer2 = (PFN_vkCmdBindIndexBuffer2)load(context, "vkCmdBindIndexBuffer2"); + table->vkCmdPushConstants2 = (PFN_vkCmdPushConstants2)load(context, "vkCmdPushConstants2"); + table->vkCmdPushDescriptorSet = (PFN_vkCmdPushDescriptorSet)load(context, "vkCmdPushDescriptorSet"); + table->vkCmdPushDescriptorSet2 = (PFN_vkCmdPushDescriptorSet2)load(context, "vkCmdPushDescriptorSet2"); + table->vkCmdPushDescriptorSetWithTemplate = (PFN_vkCmdPushDescriptorSetWithTemplate)load(context, "vkCmdPushDescriptorSetWithTemplate"); + table->vkCmdPushDescriptorSetWithTemplate2 = (PFN_vkCmdPushDescriptorSetWithTemplate2)load(context, "vkCmdPushDescriptorSetWithTemplate2"); + table->vkCmdSetLineStipple = (PFN_vkCmdSetLineStipple)load(context, "vkCmdSetLineStipple"); + table->vkCmdSetRenderingAttachmentLocations = (PFN_vkCmdSetRenderingAttachmentLocations)load(context, "vkCmdSetRenderingAttachmentLocations"); + table->vkCmdSetRenderingInputAttachmentIndices = (PFN_vkCmdSetRenderingInputAttachmentIndices)load(context, "vkCmdSetRenderingInputAttachmentIndices"); + table->vkCopyImageToImage = (PFN_vkCopyImageToImage)load(context, "vkCopyImageToImage"); + table->vkCopyImageToMemory = (PFN_vkCopyImageToMemory)load(context, "vkCopyImageToMemory"); + table->vkCopyMemoryToImage = (PFN_vkCopyMemoryToImage)load(context, "vkCopyMemoryToImage"); + table->vkGetDeviceImageSubresourceLayout = (PFN_vkGetDeviceImageSubresourceLayout)load(context, "vkGetDeviceImageSubresourceLayout"); + table->vkGetImageSubresourceLayout2 = (PFN_vkGetImageSubresourceLayout2)load(context, "vkGetImageSubresourceLayout2"); + table->vkGetRenderingAreaGranularity = (PFN_vkGetRenderingAreaGranularity)load(context, "vkGetRenderingAreaGranularity"); + table->vkMapMemory2 = (PFN_vkMapMemory2)load(context, "vkMapMemory2"); + table->vkTransitionImageLayout = (PFN_vkTransitionImageLayout)load(context, "vkTransitionImageLayout"); + table->vkUnmapMemory2 = (PFN_vkUnmapMemory2)load(context, "vkUnmapMemory2"); +#endif /* defined(VK_VERSION_1_4) */ +#if defined(VK_AMDX_shader_enqueue) + table->vkCmdDispatchGraphAMDX = (PFN_vkCmdDispatchGraphAMDX)load(context, "vkCmdDispatchGraphAMDX"); + table->vkCmdDispatchGraphIndirectAMDX = (PFN_vkCmdDispatchGraphIndirectAMDX)load(context, "vkCmdDispatchGraphIndirectAMDX"); + table->vkCmdDispatchGraphIndirectCountAMDX = (PFN_vkCmdDispatchGraphIndirectCountAMDX)load(context, "vkCmdDispatchGraphIndirectCountAMDX"); + table->vkCmdInitializeGraphScratchMemoryAMDX = (PFN_vkCmdInitializeGraphScratchMemoryAMDX)load(context, "vkCmdInitializeGraphScratchMemoryAMDX"); + table->vkCreateExecutionGraphPipelinesAMDX = (PFN_vkCreateExecutionGraphPipelinesAMDX)load(context, "vkCreateExecutionGraphPipelinesAMDX"); + table->vkGetExecutionGraphPipelineNodeIndexAMDX = (PFN_vkGetExecutionGraphPipelineNodeIndexAMDX)load(context, "vkGetExecutionGraphPipelineNodeIndexAMDX"); + table->vkGetExecutionGraphPipelineScratchSizeAMDX = (PFN_vkGetExecutionGraphPipelineScratchSizeAMDX)load(context, "vkGetExecutionGraphPipelineScratchSizeAMDX"); +#endif /* defined(VK_AMDX_shader_enqueue) */ +#if defined(VK_AMD_anti_lag) + table->vkAntiLagUpdateAMD = (PFN_vkAntiLagUpdateAMD)load(context, "vkAntiLagUpdateAMD"); +#endif /* defined(VK_AMD_anti_lag) */ +#if defined(VK_AMD_buffer_marker) + table->vkCmdWriteBufferMarkerAMD = (PFN_vkCmdWriteBufferMarkerAMD)load(context, "vkCmdWriteBufferMarkerAMD"); +#endif /* defined(VK_AMD_buffer_marker) */ +#if defined(VK_AMD_buffer_marker) && (defined(VK_VERSION_1_3) || defined(VK_KHR_synchronization2)) + table->vkCmdWriteBufferMarker2AMD = (PFN_vkCmdWriteBufferMarker2AMD)load(context, "vkCmdWriteBufferMarker2AMD"); +#endif /* defined(VK_AMD_buffer_marker) && (defined(VK_VERSION_1_3) || defined(VK_KHR_synchronization2)) */ +#if defined(VK_AMD_display_native_hdr) + table->vkSetLocalDimmingAMD = (PFN_vkSetLocalDimmingAMD)load(context, "vkSetLocalDimmingAMD"); +#endif /* defined(VK_AMD_display_native_hdr) */ +#if defined(VK_AMD_draw_indirect_count) + table->vkCmdDrawIndexedIndirectCountAMD = (PFN_vkCmdDrawIndexedIndirectCountAMD)load(context, "vkCmdDrawIndexedIndirectCountAMD"); + table->vkCmdDrawIndirectCountAMD = (PFN_vkCmdDrawIndirectCountAMD)load(context, "vkCmdDrawIndirectCountAMD"); +#endif /* defined(VK_AMD_draw_indirect_count) */ +#if defined(VK_AMD_shader_info) + table->vkGetShaderInfoAMD = (PFN_vkGetShaderInfoAMD)load(context, "vkGetShaderInfoAMD"); +#endif /* defined(VK_AMD_shader_info) */ +#if defined(VK_ANDROID_external_memory_android_hardware_buffer) + table->vkGetAndroidHardwareBufferPropertiesANDROID = (PFN_vkGetAndroidHardwareBufferPropertiesANDROID)load(context, "vkGetAndroidHardwareBufferPropertiesANDROID"); + table->vkGetMemoryAndroidHardwareBufferANDROID = (PFN_vkGetMemoryAndroidHardwareBufferANDROID)load(context, "vkGetMemoryAndroidHardwareBufferANDROID"); +#endif /* defined(VK_ANDROID_external_memory_android_hardware_buffer) */ +#if defined(VK_EXT_attachment_feedback_loop_dynamic_state) + table->vkCmdSetAttachmentFeedbackLoopEnableEXT = (PFN_vkCmdSetAttachmentFeedbackLoopEnableEXT)load(context, "vkCmdSetAttachmentFeedbackLoopEnableEXT"); +#endif /* defined(VK_EXT_attachment_feedback_loop_dynamic_state) */ +#if defined(VK_EXT_buffer_device_address) + table->vkGetBufferDeviceAddressEXT = (PFN_vkGetBufferDeviceAddressEXT)load(context, "vkGetBufferDeviceAddressEXT"); +#endif /* defined(VK_EXT_buffer_device_address) */ +#if defined(VK_EXT_calibrated_timestamps) + table->vkGetCalibratedTimestampsEXT = (PFN_vkGetCalibratedTimestampsEXT)load(context, "vkGetCalibratedTimestampsEXT"); +#endif /* defined(VK_EXT_calibrated_timestamps) */ +#if defined(VK_EXT_color_write_enable) + table->vkCmdSetColorWriteEnableEXT = (PFN_vkCmdSetColorWriteEnableEXT)load(context, "vkCmdSetColorWriteEnableEXT"); +#endif /* defined(VK_EXT_color_write_enable) */ +#if defined(VK_EXT_conditional_rendering) + table->vkCmdBeginConditionalRenderingEXT = (PFN_vkCmdBeginConditionalRenderingEXT)load(context, "vkCmdBeginConditionalRenderingEXT"); + table->vkCmdEndConditionalRenderingEXT = (PFN_vkCmdEndConditionalRenderingEXT)load(context, "vkCmdEndConditionalRenderingEXT"); +#endif /* defined(VK_EXT_conditional_rendering) */ +#if defined(VK_EXT_debug_marker) + table->vkCmdDebugMarkerBeginEXT = (PFN_vkCmdDebugMarkerBeginEXT)load(context, "vkCmdDebugMarkerBeginEXT"); + table->vkCmdDebugMarkerEndEXT = (PFN_vkCmdDebugMarkerEndEXT)load(context, "vkCmdDebugMarkerEndEXT"); + table->vkCmdDebugMarkerInsertEXT = (PFN_vkCmdDebugMarkerInsertEXT)load(context, "vkCmdDebugMarkerInsertEXT"); + table->vkDebugMarkerSetObjectNameEXT = (PFN_vkDebugMarkerSetObjectNameEXT)load(context, "vkDebugMarkerSetObjectNameEXT"); + table->vkDebugMarkerSetObjectTagEXT = (PFN_vkDebugMarkerSetObjectTagEXT)load(context, "vkDebugMarkerSetObjectTagEXT"); +#endif /* defined(VK_EXT_debug_marker) */ +#if defined(VK_EXT_depth_bias_control) + table->vkCmdSetDepthBias2EXT = (PFN_vkCmdSetDepthBias2EXT)load(context, "vkCmdSetDepthBias2EXT"); +#endif /* defined(VK_EXT_depth_bias_control) */ +#if defined(VK_EXT_descriptor_buffer) + table->vkCmdBindDescriptorBufferEmbeddedSamplersEXT = (PFN_vkCmdBindDescriptorBufferEmbeddedSamplersEXT)load(context, "vkCmdBindDescriptorBufferEmbeddedSamplersEXT"); + table->vkCmdBindDescriptorBuffersEXT = (PFN_vkCmdBindDescriptorBuffersEXT)load(context, "vkCmdBindDescriptorBuffersEXT"); + table->vkCmdSetDescriptorBufferOffsetsEXT = (PFN_vkCmdSetDescriptorBufferOffsetsEXT)load(context, "vkCmdSetDescriptorBufferOffsetsEXT"); + table->vkGetBufferOpaqueCaptureDescriptorDataEXT = (PFN_vkGetBufferOpaqueCaptureDescriptorDataEXT)load(context, "vkGetBufferOpaqueCaptureDescriptorDataEXT"); + table->vkGetDescriptorEXT = (PFN_vkGetDescriptorEXT)load(context, "vkGetDescriptorEXT"); + table->vkGetDescriptorSetLayoutBindingOffsetEXT = (PFN_vkGetDescriptorSetLayoutBindingOffsetEXT)load(context, "vkGetDescriptorSetLayoutBindingOffsetEXT"); + table->vkGetDescriptorSetLayoutSizeEXT = (PFN_vkGetDescriptorSetLayoutSizeEXT)load(context, "vkGetDescriptorSetLayoutSizeEXT"); + table->vkGetImageOpaqueCaptureDescriptorDataEXT = (PFN_vkGetImageOpaqueCaptureDescriptorDataEXT)load(context, "vkGetImageOpaqueCaptureDescriptorDataEXT"); + table->vkGetImageViewOpaqueCaptureDescriptorDataEXT = (PFN_vkGetImageViewOpaqueCaptureDescriptorDataEXT)load(context, "vkGetImageViewOpaqueCaptureDescriptorDataEXT"); + table->vkGetSamplerOpaqueCaptureDescriptorDataEXT = (PFN_vkGetSamplerOpaqueCaptureDescriptorDataEXT)load(context, "vkGetSamplerOpaqueCaptureDescriptorDataEXT"); +#endif /* defined(VK_EXT_descriptor_buffer) */ +#if defined(VK_EXT_descriptor_buffer) && (defined(VK_KHR_acceleration_structure) || defined(VK_NV_ray_tracing)) + table->vkGetAccelerationStructureOpaqueCaptureDescriptorDataEXT = (PFN_vkGetAccelerationStructureOpaqueCaptureDescriptorDataEXT)load(context, "vkGetAccelerationStructureOpaqueCaptureDescriptorDataEXT"); +#endif /* defined(VK_EXT_descriptor_buffer) && (defined(VK_KHR_acceleration_structure) || defined(VK_NV_ray_tracing)) */ +#if defined(VK_EXT_device_fault) + table->vkGetDeviceFaultInfoEXT = (PFN_vkGetDeviceFaultInfoEXT)load(context, "vkGetDeviceFaultInfoEXT"); +#endif /* defined(VK_EXT_device_fault) */ +#if defined(VK_EXT_device_generated_commands) + table->vkCmdExecuteGeneratedCommandsEXT = (PFN_vkCmdExecuteGeneratedCommandsEXT)load(context, "vkCmdExecuteGeneratedCommandsEXT"); + table->vkCmdPreprocessGeneratedCommandsEXT = (PFN_vkCmdPreprocessGeneratedCommandsEXT)load(context, "vkCmdPreprocessGeneratedCommandsEXT"); + table->vkCreateIndirectCommandsLayoutEXT = (PFN_vkCreateIndirectCommandsLayoutEXT)load(context, "vkCreateIndirectCommandsLayoutEXT"); + table->vkCreateIndirectExecutionSetEXT = (PFN_vkCreateIndirectExecutionSetEXT)load(context, "vkCreateIndirectExecutionSetEXT"); + table->vkDestroyIndirectCommandsLayoutEXT = (PFN_vkDestroyIndirectCommandsLayoutEXT)load(context, "vkDestroyIndirectCommandsLayoutEXT"); + table->vkDestroyIndirectExecutionSetEXT = (PFN_vkDestroyIndirectExecutionSetEXT)load(context, "vkDestroyIndirectExecutionSetEXT"); + table->vkGetGeneratedCommandsMemoryRequirementsEXT = (PFN_vkGetGeneratedCommandsMemoryRequirementsEXT)load(context, "vkGetGeneratedCommandsMemoryRequirementsEXT"); + table->vkUpdateIndirectExecutionSetPipelineEXT = (PFN_vkUpdateIndirectExecutionSetPipelineEXT)load(context, "vkUpdateIndirectExecutionSetPipelineEXT"); + table->vkUpdateIndirectExecutionSetShaderEXT = (PFN_vkUpdateIndirectExecutionSetShaderEXT)load(context, "vkUpdateIndirectExecutionSetShaderEXT"); +#endif /* defined(VK_EXT_device_generated_commands) */ +#if defined(VK_EXT_discard_rectangles) + table->vkCmdSetDiscardRectangleEXT = (PFN_vkCmdSetDiscardRectangleEXT)load(context, "vkCmdSetDiscardRectangleEXT"); +#endif /* defined(VK_EXT_discard_rectangles) */ +#if defined(VK_EXT_discard_rectangles) && VK_EXT_DISCARD_RECTANGLES_SPEC_VERSION >= 2 + table->vkCmdSetDiscardRectangleEnableEXT = (PFN_vkCmdSetDiscardRectangleEnableEXT)load(context, "vkCmdSetDiscardRectangleEnableEXT"); + table->vkCmdSetDiscardRectangleModeEXT = (PFN_vkCmdSetDiscardRectangleModeEXT)load(context, "vkCmdSetDiscardRectangleModeEXT"); +#endif /* defined(VK_EXT_discard_rectangles) && VK_EXT_DISCARD_RECTANGLES_SPEC_VERSION >= 2 */ +#if defined(VK_EXT_display_control) + table->vkDisplayPowerControlEXT = (PFN_vkDisplayPowerControlEXT)load(context, "vkDisplayPowerControlEXT"); + table->vkGetSwapchainCounterEXT = (PFN_vkGetSwapchainCounterEXT)load(context, "vkGetSwapchainCounterEXT"); + table->vkRegisterDeviceEventEXT = (PFN_vkRegisterDeviceEventEXT)load(context, "vkRegisterDeviceEventEXT"); + table->vkRegisterDisplayEventEXT = (PFN_vkRegisterDisplayEventEXT)load(context, "vkRegisterDisplayEventEXT"); +#endif /* defined(VK_EXT_display_control) */ +#if defined(VK_EXT_external_memory_host) + table->vkGetMemoryHostPointerPropertiesEXT = (PFN_vkGetMemoryHostPointerPropertiesEXT)load(context, "vkGetMemoryHostPointerPropertiesEXT"); +#endif /* defined(VK_EXT_external_memory_host) */ +#if defined(VK_EXT_full_screen_exclusive) + table->vkAcquireFullScreenExclusiveModeEXT = (PFN_vkAcquireFullScreenExclusiveModeEXT)load(context, "vkAcquireFullScreenExclusiveModeEXT"); + table->vkReleaseFullScreenExclusiveModeEXT = (PFN_vkReleaseFullScreenExclusiveModeEXT)load(context, "vkReleaseFullScreenExclusiveModeEXT"); +#endif /* defined(VK_EXT_full_screen_exclusive) */ +#if defined(VK_EXT_full_screen_exclusive) && (defined(VK_KHR_device_group) || defined(VK_VERSION_1_1)) + table->vkGetDeviceGroupSurfacePresentModes2EXT = (PFN_vkGetDeviceGroupSurfacePresentModes2EXT)load(context, "vkGetDeviceGroupSurfacePresentModes2EXT"); +#endif /* defined(VK_EXT_full_screen_exclusive) && (defined(VK_KHR_device_group) || defined(VK_VERSION_1_1)) */ +#if defined(VK_EXT_hdr_metadata) + table->vkSetHdrMetadataEXT = (PFN_vkSetHdrMetadataEXT)load(context, "vkSetHdrMetadataEXT"); +#endif /* defined(VK_EXT_hdr_metadata) */ +#if defined(VK_EXT_host_image_copy) + table->vkCopyImageToImageEXT = (PFN_vkCopyImageToImageEXT)load(context, "vkCopyImageToImageEXT"); + table->vkCopyImageToMemoryEXT = (PFN_vkCopyImageToMemoryEXT)load(context, "vkCopyImageToMemoryEXT"); + table->vkCopyMemoryToImageEXT = (PFN_vkCopyMemoryToImageEXT)load(context, "vkCopyMemoryToImageEXT"); + table->vkTransitionImageLayoutEXT = (PFN_vkTransitionImageLayoutEXT)load(context, "vkTransitionImageLayoutEXT"); +#endif /* defined(VK_EXT_host_image_copy) */ +#if defined(VK_EXT_host_query_reset) + table->vkResetQueryPoolEXT = (PFN_vkResetQueryPoolEXT)load(context, "vkResetQueryPoolEXT"); +#endif /* defined(VK_EXT_host_query_reset) */ +#if defined(VK_EXT_image_drm_format_modifier) + table->vkGetImageDrmFormatModifierPropertiesEXT = (PFN_vkGetImageDrmFormatModifierPropertiesEXT)load(context, "vkGetImageDrmFormatModifierPropertiesEXT"); +#endif /* defined(VK_EXT_image_drm_format_modifier) */ +#if defined(VK_EXT_line_rasterization) + table->vkCmdSetLineStippleEXT = (PFN_vkCmdSetLineStippleEXT)load(context, "vkCmdSetLineStippleEXT"); +#endif /* defined(VK_EXT_line_rasterization) */ +#if defined(VK_EXT_mesh_shader) + table->vkCmdDrawMeshTasksEXT = (PFN_vkCmdDrawMeshTasksEXT)load(context, "vkCmdDrawMeshTasksEXT"); + table->vkCmdDrawMeshTasksIndirectEXT = (PFN_vkCmdDrawMeshTasksIndirectEXT)load(context, "vkCmdDrawMeshTasksIndirectEXT"); +#endif /* defined(VK_EXT_mesh_shader) */ +#if defined(VK_EXT_mesh_shader) && (defined(VK_KHR_draw_indirect_count) || defined(VK_VERSION_1_2)) + table->vkCmdDrawMeshTasksIndirectCountEXT = (PFN_vkCmdDrawMeshTasksIndirectCountEXT)load(context, "vkCmdDrawMeshTasksIndirectCountEXT"); +#endif /* defined(VK_EXT_mesh_shader) && (defined(VK_KHR_draw_indirect_count) || defined(VK_VERSION_1_2)) */ +#if defined(VK_EXT_metal_objects) + table->vkExportMetalObjectsEXT = (PFN_vkExportMetalObjectsEXT)load(context, "vkExportMetalObjectsEXT"); +#endif /* defined(VK_EXT_metal_objects) */ +#if defined(VK_EXT_multi_draw) + table->vkCmdDrawMultiEXT = (PFN_vkCmdDrawMultiEXT)load(context, "vkCmdDrawMultiEXT"); + table->vkCmdDrawMultiIndexedEXT = (PFN_vkCmdDrawMultiIndexedEXT)load(context, "vkCmdDrawMultiIndexedEXT"); +#endif /* defined(VK_EXT_multi_draw) */ +#if defined(VK_EXT_opacity_micromap) + table->vkBuildMicromapsEXT = (PFN_vkBuildMicromapsEXT)load(context, "vkBuildMicromapsEXT"); + table->vkCmdBuildMicromapsEXT = (PFN_vkCmdBuildMicromapsEXT)load(context, "vkCmdBuildMicromapsEXT"); + table->vkCmdCopyMemoryToMicromapEXT = (PFN_vkCmdCopyMemoryToMicromapEXT)load(context, "vkCmdCopyMemoryToMicromapEXT"); + table->vkCmdCopyMicromapEXT = (PFN_vkCmdCopyMicromapEXT)load(context, "vkCmdCopyMicromapEXT"); + table->vkCmdCopyMicromapToMemoryEXT = (PFN_vkCmdCopyMicromapToMemoryEXT)load(context, "vkCmdCopyMicromapToMemoryEXT"); + table->vkCmdWriteMicromapsPropertiesEXT = (PFN_vkCmdWriteMicromapsPropertiesEXT)load(context, "vkCmdWriteMicromapsPropertiesEXT"); + table->vkCopyMemoryToMicromapEXT = (PFN_vkCopyMemoryToMicromapEXT)load(context, "vkCopyMemoryToMicromapEXT"); + table->vkCopyMicromapEXT = (PFN_vkCopyMicromapEXT)load(context, "vkCopyMicromapEXT"); + table->vkCopyMicromapToMemoryEXT = (PFN_vkCopyMicromapToMemoryEXT)load(context, "vkCopyMicromapToMemoryEXT"); + table->vkCreateMicromapEXT = (PFN_vkCreateMicromapEXT)load(context, "vkCreateMicromapEXT"); + table->vkDestroyMicromapEXT = (PFN_vkDestroyMicromapEXT)load(context, "vkDestroyMicromapEXT"); + table->vkGetDeviceMicromapCompatibilityEXT = (PFN_vkGetDeviceMicromapCompatibilityEXT)load(context, "vkGetDeviceMicromapCompatibilityEXT"); + table->vkGetMicromapBuildSizesEXT = (PFN_vkGetMicromapBuildSizesEXT)load(context, "vkGetMicromapBuildSizesEXT"); + table->vkWriteMicromapsPropertiesEXT = (PFN_vkWriteMicromapsPropertiesEXT)load(context, "vkWriteMicromapsPropertiesEXT"); +#endif /* defined(VK_EXT_opacity_micromap) */ +#if defined(VK_EXT_pageable_device_local_memory) + table->vkSetDeviceMemoryPriorityEXT = (PFN_vkSetDeviceMemoryPriorityEXT)load(context, "vkSetDeviceMemoryPriorityEXT"); +#endif /* defined(VK_EXT_pageable_device_local_memory) */ +#if defined(VK_EXT_pipeline_properties) + table->vkGetPipelinePropertiesEXT = (PFN_vkGetPipelinePropertiesEXT)load(context, "vkGetPipelinePropertiesEXT"); +#endif /* defined(VK_EXT_pipeline_properties) */ +#if defined(VK_EXT_private_data) + table->vkCreatePrivateDataSlotEXT = (PFN_vkCreatePrivateDataSlotEXT)load(context, "vkCreatePrivateDataSlotEXT"); + table->vkDestroyPrivateDataSlotEXT = (PFN_vkDestroyPrivateDataSlotEXT)load(context, "vkDestroyPrivateDataSlotEXT"); + table->vkGetPrivateDataEXT = (PFN_vkGetPrivateDataEXT)load(context, "vkGetPrivateDataEXT"); + table->vkSetPrivateDataEXT = (PFN_vkSetPrivateDataEXT)load(context, "vkSetPrivateDataEXT"); +#endif /* defined(VK_EXT_private_data) */ +#if defined(VK_EXT_sample_locations) + table->vkCmdSetSampleLocationsEXT = (PFN_vkCmdSetSampleLocationsEXT)load(context, "vkCmdSetSampleLocationsEXT"); +#endif /* defined(VK_EXT_sample_locations) */ +#if defined(VK_EXT_shader_module_identifier) + table->vkGetShaderModuleCreateInfoIdentifierEXT = (PFN_vkGetShaderModuleCreateInfoIdentifierEXT)load(context, "vkGetShaderModuleCreateInfoIdentifierEXT"); + table->vkGetShaderModuleIdentifierEXT = (PFN_vkGetShaderModuleIdentifierEXT)load(context, "vkGetShaderModuleIdentifierEXT"); +#endif /* defined(VK_EXT_shader_module_identifier) */ +#if defined(VK_EXT_shader_object) + table->vkCmdBindShadersEXT = (PFN_vkCmdBindShadersEXT)load(context, "vkCmdBindShadersEXT"); + table->vkCreateShadersEXT = (PFN_vkCreateShadersEXT)load(context, "vkCreateShadersEXT"); + table->vkDestroyShaderEXT = (PFN_vkDestroyShaderEXT)load(context, "vkDestroyShaderEXT"); + table->vkGetShaderBinaryDataEXT = (PFN_vkGetShaderBinaryDataEXT)load(context, "vkGetShaderBinaryDataEXT"); +#endif /* defined(VK_EXT_shader_object) */ +#if defined(VK_EXT_swapchain_maintenance1) + table->vkReleaseSwapchainImagesEXT = (PFN_vkReleaseSwapchainImagesEXT)load(context, "vkReleaseSwapchainImagesEXT"); +#endif /* defined(VK_EXT_swapchain_maintenance1) */ +#if defined(VK_EXT_transform_feedback) + table->vkCmdBeginQueryIndexedEXT = (PFN_vkCmdBeginQueryIndexedEXT)load(context, "vkCmdBeginQueryIndexedEXT"); + table->vkCmdBeginTransformFeedbackEXT = (PFN_vkCmdBeginTransformFeedbackEXT)load(context, "vkCmdBeginTransformFeedbackEXT"); + table->vkCmdBindTransformFeedbackBuffersEXT = (PFN_vkCmdBindTransformFeedbackBuffersEXT)load(context, "vkCmdBindTransformFeedbackBuffersEXT"); + table->vkCmdDrawIndirectByteCountEXT = (PFN_vkCmdDrawIndirectByteCountEXT)load(context, "vkCmdDrawIndirectByteCountEXT"); + table->vkCmdEndQueryIndexedEXT = (PFN_vkCmdEndQueryIndexedEXT)load(context, "vkCmdEndQueryIndexedEXT"); + table->vkCmdEndTransformFeedbackEXT = (PFN_vkCmdEndTransformFeedbackEXT)load(context, "vkCmdEndTransformFeedbackEXT"); +#endif /* defined(VK_EXT_transform_feedback) */ +#if defined(VK_EXT_validation_cache) + table->vkCreateValidationCacheEXT = (PFN_vkCreateValidationCacheEXT)load(context, "vkCreateValidationCacheEXT"); + table->vkDestroyValidationCacheEXT = (PFN_vkDestroyValidationCacheEXT)load(context, "vkDestroyValidationCacheEXT"); + table->vkGetValidationCacheDataEXT = (PFN_vkGetValidationCacheDataEXT)load(context, "vkGetValidationCacheDataEXT"); + table->vkMergeValidationCachesEXT = (PFN_vkMergeValidationCachesEXT)load(context, "vkMergeValidationCachesEXT"); +#endif /* defined(VK_EXT_validation_cache) */ +#if defined(VK_FUCHSIA_buffer_collection) + table->vkCreateBufferCollectionFUCHSIA = (PFN_vkCreateBufferCollectionFUCHSIA)load(context, "vkCreateBufferCollectionFUCHSIA"); + table->vkDestroyBufferCollectionFUCHSIA = (PFN_vkDestroyBufferCollectionFUCHSIA)load(context, "vkDestroyBufferCollectionFUCHSIA"); + table->vkGetBufferCollectionPropertiesFUCHSIA = (PFN_vkGetBufferCollectionPropertiesFUCHSIA)load(context, "vkGetBufferCollectionPropertiesFUCHSIA"); + table->vkSetBufferCollectionBufferConstraintsFUCHSIA = (PFN_vkSetBufferCollectionBufferConstraintsFUCHSIA)load(context, "vkSetBufferCollectionBufferConstraintsFUCHSIA"); + table->vkSetBufferCollectionImageConstraintsFUCHSIA = (PFN_vkSetBufferCollectionImageConstraintsFUCHSIA)load(context, "vkSetBufferCollectionImageConstraintsFUCHSIA"); +#endif /* defined(VK_FUCHSIA_buffer_collection) */ +#if defined(VK_FUCHSIA_external_memory) + table->vkGetMemoryZirconHandleFUCHSIA = (PFN_vkGetMemoryZirconHandleFUCHSIA)load(context, "vkGetMemoryZirconHandleFUCHSIA"); + table->vkGetMemoryZirconHandlePropertiesFUCHSIA = (PFN_vkGetMemoryZirconHandlePropertiesFUCHSIA)load(context, "vkGetMemoryZirconHandlePropertiesFUCHSIA"); +#endif /* defined(VK_FUCHSIA_external_memory) */ +#if defined(VK_FUCHSIA_external_semaphore) + table->vkGetSemaphoreZirconHandleFUCHSIA = (PFN_vkGetSemaphoreZirconHandleFUCHSIA)load(context, "vkGetSemaphoreZirconHandleFUCHSIA"); + table->vkImportSemaphoreZirconHandleFUCHSIA = (PFN_vkImportSemaphoreZirconHandleFUCHSIA)load(context, "vkImportSemaphoreZirconHandleFUCHSIA"); +#endif /* defined(VK_FUCHSIA_external_semaphore) */ +#if defined(VK_GOOGLE_display_timing) + table->vkGetPastPresentationTimingGOOGLE = (PFN_vkGetPastPresentationTimingGOOGLE)load(context, "vkGetPastPresentationTimingGOOGLE"); + table->vkGetRefreshCycleDurationGOOGLE = (PFN_vkGetRefreshCycleDurationGOOGLE)load(context, "vkGetRefreshCycleDurationGOOGLE"); +#endif /* defined(VK_GOOGLE_display_timing) */ +#if defined(VK_HUAWEI_cluster_culling_shader) + table->vkCmdDrawClusterHUAWEI = (PFN_vkCmdDrawClusterHUAWEI)load(context, "vkCmdDrawClusterHUAWEI"); + table->vkCmdDrawClusterIndirectHUAWEI = (PFN_vkCmdDrawClusterIndirectHUAWEI)load(context, "vkCmdDrawClusterIndirectHUAWEI"); +#endif /* defined(VK_HUAWEI_cluster_culling_shader) */ +#if defined(VK_HUAWEI_invocation_mask) + table->vkCmdBindInvocationMaskHUAWEI = (PFN_vkCmdBindInvocationMaskHUAWEI)load(context, "vkCmdBindInvocationMaskHUAWEI"); +#endif /* defined(VK_HUAWEI_invocation_mask) */ +#if defined(VK_HUAWEI_subpass_shading) && VK_HUAWEI_SUBPASS_SHADING_SPEC_VERSION >= 2 + table->vkGetDeviceSubpassShadingMaxWorkgroupSizeHUAWEI = (PFN_vkGetDeviceSubpassShadingMaxWorkgroupSizeHUAWEI)load(context, "vkGetDeviceSubpassShadingMaxWorkgroupSizeHUAWEI"); +#endif /* defined(VK_HUAWEI_subpass_shading) && VK_HUAWEI_SUBPASS_SHADING_SPEC_VERSION >= 2 */ +#if defined(VK_HUAWEI_subpass_shading) + table->vkCmdSubpassShadingHUAWEI = (PFN_vkCmdSubpassShadingHUAWEI)load(context, "vkCmdSubpassShadingHUAWEI"); +#endif /* defined(VK_HUAWEI_subpass_shading) */ +#if defined(VK_INTEL_performance_query) + table->vkAcquirePerformanceConfigurationINTEL = (PFN_vkAcquirePerformanceConfigurationINTEL)load(context, "vkAcquirePerformanceConfigurationINTEL"); + table->vkCmdSetPerformanceMarkerINTEL = (PFN_vkCmdSetPerformanceMarkerINTEL)load(context, "vkCmdSetPerformanceMarkerINTEL"); + table->vkCmdSetPerformanceOverrideINTEL = (PFN_vkCmdSetPerformanceOverrideINTEL)load(context, "vkCmdSetPerformanceOverrideINTEL"); + table->vkCmdSetPerformanceStreamMarkerINTEL = (PFN_vkCmdSetPerformanceStreamMarkerINTEL)load(context, "vkCmdSetPerformanceStreamMarkerINTEL"); + table->vkGetPerformanceParameterINTEL = (PFN_vkGetPerformanceParameterINTEL)load(context, "vkGetPerformanceParameterINTEL"); + table->vkInitializePerformanceApiINTEL = (PFN_vkInitializePerformanceApiINTEL)load(context, "vkInitializePerformanceApiINTEL"); + table->vkQueueSetPerformanceConfigurationINTEL = (PFN_vkQueueSetPerformanceConfigurationINTEL)load(context, "vkQueueSetPerformanceConfigurationINTEL"); + table->vkReleasePerformanceConfigurationINTEL = (PFN_vkReleasePerformanceConfigurationINTEL)load(context, "vkReleasePerformanceConfigurationINTEL"); + table->vkUninitializePerformanceApiINTEL = (PFN_vkUninitializePerformanceApiINTEL)load(context, "vkUninitializePerformanceApiINTEL"); +#endif /* defined(VK_INTEL_performance_query) */ +#if defined(VK_KHR_acceleration_structure) + table->vkBuildAccelerationStructuresKHR = (PFN_vkBuildAccelerationStructuresKHR)load(context, "vkBuildAccelerationStructuresKHR"); + table->vkCmdBuildAccelerationStructuresIndirectKHR = (PFN_vkCmdBuildAccelerationStructuresIndirectKHR)load(context, "vkCmdBuildAccelerationStructuresIndirectKHR"); + table->vkCmdBuildAccelerationStructuresKHR = (PFN_vkCmdBuildAccelerationStructuresKHR)load(context, "vkCmdBuildAccelerationStructuresKHR"); + table->vkCmdCopyAccelerationStructureKHR = (PFN_vkCmdCopyAccelerationStructureKHR)load(context, "vkCmdCopyAccelerationStructureKHR"); + table->vkCmdCopyAccelerationStructureToMemoryKHR = (PFN_vkCmdCopyAccelerationStructureToMemoryKHR)load(context, "vkCmdCopyAccelerationStructureToMemoryKHR"); + table->vkCmdCopyMemoryToAccelerationStructureKHR = (PFN_vkCmdCopyMemoryToAccelerationStructureKHR)load(context, "vkCmdCopyMemoryToAccelerationStructureKHR"); + table->vkCmdWriteAccelerationStructuresPropertiesKHR = (PFN_vkCmdWriteAccelerationStructuresPropertiesKHR)load(context, "vkCmdWriteAccelerationStructuresPropertiesKHR"); + table->vkCopyAccelerationStructureKHR = (PFN_vkCopyAccelerationStructureKHR)load(context, "vkCopyAccelerationStructureKHR"); + table->vkCopyAccelerationStructureToMemoryKHR = (PFN_vkCopyAccelerationStructureToMemoryKHR)load(context, "vkCopyAccelerationStructureToMemoryKHR"); + table->vkCopyMemoryToAccelerationStructureKHR = (PFN_vkCopyMemoryToAccelerationStructureKHR)load(context, "vkCopyMemoryToAccelerationStructureKHR"); + table->vkCreateAccelerationStructureKHR = (PFN_vkCreateAccelerationStructureKHR)load(context, "vkCreateAccelerationStructureKHR"); + table->vkDestroyAccelerationStructureKHR = (PFN_vkDestroyAccelerationStructureKHR)load(context, "vkDestroyAccelerationStructureKHR"); + table->vkGetAccelerationStructureBuildSizesKHR = (PFN_vkGetAccelerationStructureBuildSizesKHR)load(context, "vkGetAccelerationStructureBuildSizesKHR"); + table->vkGetAccelerationStructureDeviceAddressKHR = (PFN_vkGetAccelerationStructureDeviceAddressKHR)load(context, "vkGetAccelerationStructureDeviceAddressKHR"); + table->vkGetDeviceAccelerationStructureCompatibilityKHR = (PFN_vkGetDeviceAccelerationStructureCompatibilityKHR)load(context, "vkGetDeviceAccelerationStructureCompatibilityKHR"); + table->vkWriteAccelerationStructuresPropertiesKHR = (PFN_vkWriteAccelerationStructuresPropertiesKHR)load(context, "vkWriteAccelerationStructuresPropertiesKHR"); +#endif /* defined(VK_KHR_acceleration_structure) */ +#if defined(VK_KHR_bind_memory2) + table->vkBindBufferMemory2KHR = (PFN_vkBindBufferMemory2KHR)load(context, "vkBindBufferMemory2KHR"); + table->vkBindImageMemory2KHR = (PFN_vkBindImageMemory2KHR)load(context, "vkBindImageMemory2KHR"); +#endif /* defined(VK_KHR_bind_memory2) */ +#if defined(VK_KHR_buffer_device_address) + table->vkGetBufferDeviceAddressKHR = (PFN_vkGetBufferDeviceAddressKHR)load(context, "vkGetBufferDeviceAddressKHR"); + table->vkGetBufferOpaqueCaptureAddressKHR = (PFN_vkGetBufferOpaqueCaptureAddressKHR)load(context, "vkGetBufferOpaqueCaptureAddressKHR"); + table->vkGetDeviceMemoryOpaqueCaptureAddressKHR = (PFN_vkGetDeviceMemoryOpaqueCaptureAddressKHR)load(context, "vkGetDeviceMemoryOpaqueCaptureAddressKHR"); +#endif /* defined(VK_KHR_buffer_device_address) */ +#if defined(VK_KHR_calibrated_timestamps) + table->vkGetCalibratedTimestampsKHR = (PFN_vkGetCalibratedTimestampsKHR)load(context, "vkGetCalibratedTimestampsKHR"); +#endif /* defined(VK_KHR_calibrated_timestamps) */ +#if defined(VK_KHR_copy_commands2) + table->vkCmdBlitImage2KHR = (PFN_vkCmdBlitImage2KHR)load(context, "vkCmdBlitImage2KHR"); + table->vkCmdCopyBuffer2KHR = (PFN_vkCmdCopyBuffer2KHR)load(context, "vkCmdCopyBuffer2KHR"); + table->vkCmdCopyBufferToImage2KHR = (PFN_vkCmdCopyBufferToImage2KHR)load(context, "vkCmdCopyBufferToImage2KHR"); + table->vkCmdCopyImage2KHR = (PFN_vkCmdCopyImage2KHR)load(context, "vkCmdCopyImage2KHR"); + table->vkCmdCopyImageToBuffer2KHR = (PFN_vkCmdCopyImageToBuffer2KHR)load(context, "vkCmdCopyImageToBuffer2KHR"); + table->vkCmdResolveImage2KHR = (PFN_vkCmdResolveImage2KHR)load(context, "vkCmdResolveImage2KHR"); +#endif /* defined(VK_KHR_copy_commands2) */ +#if defined(VK_KHR_create_renderpass2) + table->vkCmdBeginRenderPass2KHR = (PFN_vkCmdBeginRenderPass2KHR)load(context, "vkCmdBeginRenderPass2KHR"); + table->vkCmdEndRenderPass2KHR = (PFN_vkCmdEndRenderPass2KHR)load(context, "vkCmdEndRenderPass2KHR"); + table->vkCmdNextSubpass2KHR = (PFN_vkCmdNextSubpass2KHR)load(context, "vkCmdNextSubpass2KHR"); + table->vkCreateRenderPass2KHR = (PFN_vkCreateRenderPass2KHR)load(context, "vkCreateRenderPass2KHR"); +#endif /* defined(VK_KHR_create_renderpass2) */ +#if defined(VK_KHR_deferred_host_operations) + table->vkCreateDeferredOperationKHR = (PFN_vkCreateDeferredOperationKHR)load(context, "vkCreateDeferredOperationKHR"); + table->vkDeferredOperationJoinKHR = (PFN_vkDeferredOperationJoinKHR)load(context, "vkDeferredOperationJoinKHR"); + table->vkDestroyDeferredOperationKHR = (PFN_vkDestroyDeferredOperationKHR)load(context, "vkDestroyDeferredOperationKHR"); + table->vkGetDeferredOperationMaxConcurrencyKHR = (PFN_vkGetDeferredOperationMaxConcurrencyKHR)load(context, "vkGetDeferredOperationMaxConcurrencyKHR"); + table->vkGetDeferredOperationResultKHR = (PFN_vkGetDeferredOperationResultKHR)load(context, "vkGetDeferredOperationResultKHR"); +#endif /* defined(VK_KHR_deferred_host_operations) */ +#if defined(VK_KHR_descriptor_update_template) + table->vkCreateDescriptorUpdateTemplateKHR = (PFN_vkCreateDescriptorUpdateTemplateKHR)load(context, "vkCreateDescriptorUpdateTemplateKHR"); + table->vkDestroyDescriptorUpdateTemplateKHR = (PFN_vkDestroyDescriptorUpdateTemplateKHR)load(context, "vkDestroyDescriptorUpdateTemplateKHR"); + table->vkUpdateDescriptorSetWithTemplateKHR = (PFN_vkUpdateDescriptorSetWithTemplateKHR)load(context, "vkUpdateDescriptorSetWithTemplateKHR"); +#endif /* defined(VK_KHR_descriptor_update_template) */ +#if defined(VK_KHR_device_group) + table->vkCmdDispatchBaseKHR = (PFN_vkCmdDispatchBaseKHR)load(context, "vkCmdDispatchBaseKHR"); + table->vkCmdSetDeviceMaskKHR = (PFN_vkCmdSetDeviceMaskKHR)load(context, "vkCmdSetDeviceMaskKHR"); + table->vkGetDeviceGroupPeerMemoryFeaturesKHR = (PFN_vkGetDeviceGroupPeerMemoryFeaturesKHR)load(context, "vkGetDeviceGroupPeerMemoryFeaturesKHR"); +#endif /* defined(VK_KHR_device_group) */ +#if defined(VK_KHR_display_swapchain) + table->vkCreateSharedSwapchainsKHR = (PFN_vkCreateSharedSwapchainsKHR)load(context, "vkCreateSharedSwapchainsKHR"); +#endif /* defined(VK_KHR_display_swapchain) */ +#if defined(VK_KHR_draw_indirect_count) + table->vkCmdDrawIndexedIndirectCountKHR = (PFN_vkCmdDrawIndexedIndirectCountKHR)load(context, "vkCmdDrawIndexedIndirectCountKHR"); + table->vkCmdDrawIndirectCountKHR = (PFN_vkCmdDrawIndirectCountKHR)load(context, "vkCmdDrawIndirectCountKHR"); +#endif /* defined(VK_KHR_draw_indirect_count) */ +#if defined(VK_KHR_dynamic_rendering) + table->vkCmdBeginRenderingKHR = (PFN_vkCmdBeginRenderingKHR)load(context, "vkCmdBeginRenderingKHR"); + table->vkCmdEndRenderingKHR = (PFN_vkCmdEndRenderingKHR)load(context, "vkCmdEndRenderingKHR"); +#endif /* defined(VK_KHR_dynamic_rendering) */ +#if defined(VK_KHR_dynamic_rendering_local_read) + table->vkCmdSetRenderingAttachmentLocationsKHR = (PFN_vkCmdSetRenderingAttachmentLocationsKHR)load(context, "vkCmdSetRenderingAttachmentLocationsKHR"); + table->vkCmdSetRenderingInputAttachmentIndicesKHR = (PFN_vkCmdSetRenderingInputAttachmentIndicesKHR)load(context, "vkCmdSetRenderingInputAttachmentIndicesKHR"); +#endif /* defined(VK_KHR_dynamic_rendering_local_read) */ +#if defined(VK_KHR_external_fence_fd) + table->vkGetFenceFdKHR = (PFN_vkGetFenceFdKHR)load(context, "vkGetFenceFdKHR"); + table->vkImportFenceFdKHR = (PFN_vkImportFenceFdKHR)load(context, "vkImportFenceFdKHR"); +#endif /* defined(VK_KHR_external_fence_fd) */ +#if defined(VK_KHR_external_fence_win32) + table->vkGetFenceWin32HandleKHR = (PFN_vkGetFenceWin32HandleKHR)load(context, "vkGetFenceWin32HandleKHR"); + table->vkImportFenceWin32HandleKHR = (PFN_vkImportFenceWin32HandleKHR)load(context, "vkImportFenceWin32HandleKHR"); +#endif /* defined(VK_KHR_external_fence_win32) */ +#if defined(VK_KHR_external_memory_fd) + table->vkGetMemoryFdKHR = (PFN_vkGetMemoryFdKHR)load(context, "vkGetMemoryFdKHR"); + table->vkGetMemoryFdPropertiesKHR = (PFN_vkGetMemoryFdPropertiesKHR)load(context, "vkGetMemoryFdPropertiesKHR"); +#endif /* defined(VK_KHR_external_memory_fd) */ +#if defined(VK_KHR_external_memory_win32) + table->vkGetMemoryWin32HandleKHR = (PFN_vkGetMemoryWin32HandleKHR)load(context, "vkGetMemoryWin32HandleKHR"); + table->vkGetMemoryWin32HandlePropertiesKHR = (PFN_vkGetMemoryWin32HandlePropertiesKHR)load(context, "vkGetMemoryWin32HandlePropertiesKHR"); +#endif /* defined(VK_KHR_external_memory_win32) */ +#if defined(VK_KHR_external_semaphore_fd) + table->vkGetSemaphoreFdKHR = (PFN_vkGetSemaphoreFdKHR)load(context, "vkGetSemaphoreFdKHR"); + table->vkImportSemaphoreFdKHR = (PFN_vkImportSemaphoreFdKHR)load(context, "vkImportSemaphoreFdKHR"); +#endif /* defined(VK_KHR_external_semaphore_fd) */ +#if defined(VK_KHR_external_semaphore_win32) + table->vkGetSemaphoreWin32HandleKHR = (PFN_vkGetSemaphoreWin32HandleKHR)load(context, "vkGetSemaphoreWin32HandleKHR"); + table->vkImportSemaphoreWin32HandleKHR = (PFN_vkImportSemaphoreWin32HandleKHR)load(context, "vkImportSemaphoreWin32HandleKHR"); +#endif /* defined(VK_KHR_external_semaphore_win32) */ +#if defined(VK_KHR_fragment_shading_rate) + table->vkCmdSetFragmentShadingRateKHR = (PFN_vkCmdSetFragmentShadingRateKHR)load(context, "vkCmdSetFragmentShadingRateKHR"); +#endif /* defined(VK_KHR_fragment_shading_rate) */ +#if defined(VK_KHR_get_memory_requirements2) + table->vkGetBufferMemoryRequirements2KHR = (PFN_vkGetBufferMemoryRequirements2KHR)load(context, "vkGetBufferMemoryRequirements2KHR"); + table->vkGetImageMemoryRequirements2KHR = (PFN_vkGetImageMemoryRequirements2KHR)load(context, "vkGetImageMemoryRequirements2KHR"); + table->vkGetImageSparseMemoryRequirements2KHR = (PFN_vkGetImageSparseMemoryRequirements2KHR)load(context, "vkGetImageSparseMemoryRequirements2KHR"); +#endif /* defined(VK_KHR_get_memory_requirements2) */ +#if defined(VK_KHR_line_rasterization) + table->vkCmdSetLineStippleKHR = (PFN_vkCmdSetLineStippleKHR)load(context, "vkCmdSetLineStippleKHR"); +#endif /* defined(VK_KHR_line_rasterization) */ +#if defined(VK_KHR_maintenance1) + table->vkTrimCommandPoolKHR = (PFN_vkTrimCommandPoolKHR)load(context, "vkTrimCommandPoolKHR"); +#endif /* defined(VK_KHR_maintenance1) */ +#if defined(VK_KHR_maintenance3) + table->vkGetDescriptorSetLayoutSupportKHR = (PFN_vkGetDescriptorSetLayoutSupportKHR)load(context, "vkGetDescriptorSetLayoutSupportKHR"); +#endif /* defined(VK_KHR_maintenance3) */ +#if defined(VK_KHR_maintenance4) + table->vkGetDeviceBufferMemoryRequirementsKHR = (PFN_vkGetDeviceBufferMemoryRequirementsKHR)load(context, "vkGetDeviceBufferMemoryRequirementsKHR"); + table->vkGetDeviceImageMemoryRequirementsKHR = (PFN_vkGetDeviceImageMemoryRequirementsKHR)load(context, "vkGetDeviceImageMemoryRequirementsKHR"); + table->vkGetDeviceImageSparseMemoryRequirementsKHR = (PFN_vkGetDeviceImageSparseMemoryRequirementsKHR)load(context, "vkGetDeviceImageSparseMemoryRequirementsKHR"); +#endif /* defined(VK_KHR_maintenance4) */ +#if defined(VK_KHR_maintenance5) + table->vkCmdBindIndexBuffer2KHR = (PFN_vkCmdBindIndexBuffer2KHR)load(context, "vkCmdBindIndexBuffer2KHR"); + table->vkGetDeviceImageSubresourceLayoutKHR = (PFN_vkGetDeviceImageSubresourceLayoutKHR)load(context, "vkGetDeviceImageSubresourceLayoutKHR"); + table->vkGetImageSubresourceLayout2KHR = (PFN_vkGetImageSubresourceLayout2KHR)load(context, "vkGetImageSubresourceLayout2KHR"); + table->vkGetRenderingAreaGranularityKHR = (PFN_vkGetRenderingAreaGranularityKHR)load(context, "vkGetRenderingAreaGranularityKHR"); +#endif /* defined(VK_KHR_maintenance5) */ +#if defined(VK_KHR_maintenance6) + table->vkCmdBindDescriptorSets2KHR = (PFN_vkCmdBindDescriptorSets2KHR)load(context, "vkCmdBindDescriptorSets2KHR"); + table->vkCmdPushConstants2KHR = (PFN_vkCmdPushConstants2KHR)load(context, "vkCmdPushConstants2KHR"); +#endif /* defined(VK_KHR_maintenance6) */ +#if defined(VK_KHR_maintenance6) && defined(VK_KHR_push_descriptor) + table->vkCmdPushDescriptorSet2KHR = (PFN_vkCmdPushDescriptorSet2KHR)load(context, "vkCmdPushDescriptorSet2KHR"); + table->vkCmdPushDescriptorSetWithTemplate2KHR = (PFN_vkCmdPushDescriptorSetWithTemplate2KHR)load(context, "vkCmdPushDescriptorSetWithTemplate2KHR"); +#endif /* defined(VK_KHR_maintenance6) && defined(VK_KHR_push_descriptor) */ +#if defined(VK_KHR_maintenance6) && defined(VK_EXT_descriptor_buffer) + table->vkCmdBindDescriptorBufferEmbeddedSamplers2EXT = (PFN_vkCmdBindDescriptorBufferEmbeddedSamplers2EXT)load(context, "vkCmdBindDescriptorBufferEmbeddedSamplers2EXT"); + table->vkCmdSetDescriptorBufferOffsets2EXT = (PFN_vkCmdSetDescriptorBufferOffsets2EXT)load(context, "vkCmdSetDescriptorBufferOffsets2EXT"); +#endif /* defined(VK_KHR_maintenance6) && defined(VK_EXT_descriptor_buffer) */ +#if defined(VK_KHR_map_memory2) + table->vkMapMemory2KHR = (PFN_vkMapMemory2KHR)load(context, "vkMapMemory2KHR"); + table->vkUnmapMemory2KHR = (PFN_vkUnmapMemory2KHR)load(context, "vkUnmapMemory2KHR"); +#endif /* defined(VK_KHR_map_memory2) */ +#if defined(VK_KHR_performance_query) + table->vkAcquireProfilingLockKHR = (PFN_vkAcquireProfilingLockKHR)load(context, "vkAcquireProfilingLockKHR"); + table->vkReleaseProfilingLockKHR = (PFN_vkReleaseProfilingLockKHR)load(context, "vkReleaseProfilingLockKHR"); +#endif /* defined(VK_KHR_performance_query) */ +#if defined(VK_KHR_pipeline_binary) + table->vkCreatePipelineBinariesKHR = (PFN_vkCreatePipelineBinariesKHR)load(context, "vkCreatePipelineBinariesKHR"); + table->vkDestroyPipelineBinaryKHR = (PFN_vkDestroyPipelineBinaryKHR)load(context, "vkDestroyPipelineBinaryKHR"); + table->vkGetPipelineBinaryDataKHR = (PFN_vkGetPipelineBinaryDataKHR)load(context, "vkGetPipelineBinaryDataKHR"); + table->vkGetPipelineKeyKHR = (PFN_vkGetPipelineKeyKHR)load(context, "vkGetPipelineKeyKHR"); + table->vkReleaseCapturedPipelineDataKHR = (PFN_vkReleaseCapturedPipelineDataKHR)load(context, "vkReleaseCapturedPipelineDataKHR"); +#endif /* defined(VK_KHR_pipeline_binary) */ +#if defined(VK_KHR_pipeline_executable_properties) + table->vkGetPipelineExecutableInternalRepresentationsKHR = (PFN_vkGetPipelineExecutableInternalRepresentationsKHR)load(context, "vkGetPipelineExecutableInternalRepresentationsKHR"); + table->vkGetPipelineExecutablePropertiesKHR = (PFN_vkGetPipelineExecutablePropertiesKHR)load(context, "vkGetPipelineExecutablePropertiesKHR"); + table->vkGetPipelineExecutableStatisticsKHR = (PFN_vkGetPipelineExecutableStatisticsKHR)load(context, "vkGetPipelineExecutableStatisticsKHR"); +#endif /* defined(VK_KHR_pipeline_executable_properties) */ +#if defined(VK_KHR_present_wait) + table->vkWaitForPresentKHR = (PFN_vkWaitForPresentKHR)load(context, "vkWaitForPresentKHR"); +#endif /* defined(VK_KHR_present_wait) */ +#if defined(VK_KHR_push_descriptor) + table->vkCmdPushDescriptorSetKHR = (PFN_vkCmdPushDescriptorSetKHR)load(context, "vkCmdPushDescriptorSetKHR"); +#endif /* defined(VK_KHR_push_descriptor) */ +#if defined(VK_KHR_ray_tracing_maintenance1) && defined(VK_KHR_ray_tracing_pipeline) + table->vkCmdTraceRaysIndirect2KHR = (PFN_vkCmdTraceRaysIndirect2KHR)load(context, "vkCmdTraceRaysIndirect2KHR"); +#endif /* defined(VK_KHR_ray_tracing_maintenance1) && defined(VK_KHR_ray_tracing_pipeline) */ +#if defined(VK_KHR_ray_tracing_pipeline) + table->vkCmdSetRayTracingPipelineStackSizeKHR = (PFN_vkCmdSetRayTracingPipelineStackSizeKHR)load(context, "vkCmdSetRayTracingPipelineStackSizeKHR"); + table->vkCmdTraceRaysIndirectKHR = (PFN_vkCmdTraceRaysIndirectKHR)load(context, "vkCmdTraceRaysIndirectKHR"); + table->vkCmdTraceRaysKHR = (PFN_vkCmdTraceRaysKHR)load(context, "vkCmdTraceRaysKHR"); + table->vkCreateRayTracingPipelinesKHR = (PFN_vkCreateRayTracingPipelinesKHR)load(context, "vkCreateRayTracingPipelinesKHR"); + table->vkGetRayTracingCaptureReplayShaderGroupHandlesKHR = (PFN_vkGetRayTracingCaptureReplayShaderGroupHandlesKHR)load(context, "vkGetRayTracingCaptureReplayShaderGroupHandlesKHR"); + table->vkGetRayTracingShaderGroupHandlesKHR = (PFN_vkGetRayTracingShaderGroupHandlesKHR)load(context, "vkGetRayTracingShaderGroupHandlesKHR"); + table->vkGetRayTracingShaderGroupStackSizeKHR = (PFN_vkGetRayTracingShaderGroupStackSizeKHR)load(context, "vkGetRayTracingShaderGroupStackSizeKHR"); +#endif /* defined(VK_KHR_ray_tracing_pipeline) */ +#if defined(VK_KHR_sampler_ycbcr_conversion) + table->vkCreateSamplerYcbcrConversionKHR = (PFN_vkCreateSamplerYcbcrConversionKHR)load(context, "vkCreateSamplerYcbcrConversionKHR"); + table->vkDestroySamplerYcbcrConversionKHR = (PFN_vkDestroySamplerYcbcrConversionKHR)load(context, "vkDestroySamplerYcbcrConversionKHR"); +#endif /* defined(VK_KHR_sampler_ycbcr_conversion) */ +#if defined(VK_KHR_shared_presentable_image) + table->vkGetSwapchainStatusKHR = (PFN_vkGetSwapchainStatusKHR)load(context, "vkGetSwapchainStatusKHR"); +#endif /* defined(VK_KHR_shared_presentable_image) */ +#if defined(VK_KHR_swapchain) + table->vkAcquireNextImageKHR = (PFN_vkAcquireNextImageKHR)load(context, "vkAcquireNextImageKHR"); + table->vkCreateSwapchainKHR = (PFN_vkCreateSwapchainKHR)load(context, "vkCreateSwapchainKHR"); + table->vkDestroySwapchainKHR = (PFN_vkDestroySwapchainKHR)load(context, "vkDestroySwapchainKHR"); + table->vkGetSwapchainImagesKHR = (PFN_vkGetSwapchainImagesKHR)load(context, "vkGetSwapchainImagesKHR"); + table->vkQueuePresentKHR = (PFN_vkQueuePresentKHR)load(context, "vkQueuePresentKHR"); +#endif /* defined(VK_KHR_swapchain) */ +#if defined(VK_KHR_synchronization2) + table->vkCmdPipelineBarrier2KHR = (PFN_vkCmdPipelineBarrier2KHR)load(context, "vkCmdPipelineBarrier2KHR"); + table->vkCmdResetEvent2KHR = (PFN_vkCmdResetEvent2KHR)load(context, "vkCmdResetEvent2KHR"); + table->vkCmdSetEvent2KHR = (PFN_vkCmdSetEvent2KHR)load(context, "vkCmdSetEvent2KHR"); + table->vkCmdWaitEvents2KHR = (PFN_vkCmdWaitEvents2KHR)load(context, "vkCmdWaitEvents2KHR"); + table->vkCmdWriteTimestamp2KHR = (PFN_vkCmdWriteTimestamp2KHR)load(context, "vkCmdWriteTimestamp2KHR"); + table->vkQueueSubmit2KHR = (PFN_vkQueueSubmit2KHR)load(context, "vkQueueSubmit2KHR"); +#endif /* defined(VK_KHR_synchronization2) */ +#if defined(VK_KHR_timeline_semaphore) + table->vkGetSemaphoreCounterValueKHR = (PFN_vkGetSemaphoreCounterValueKHR)load(context, "vkGetSemaphoreCounterValueKHR"); + table->vkSignalSemaphoreKHR = (PFN_vkSignalSemaphoreKHR)load(context, "vkSignalSemaphoreKHR"); + table->vkWaitSemaphoresKHR = (PFN_vkWaitSemaphoresKHR)load(context, "vkWaitSemaphoresKHR"); +#endif /* defined(VK_KHR_timeline_semaphore) */ +#if defined(VK_KHR_video_decode_queue) + table->vkCmdDecodeVideoKHR = (PFN_vkCmdDecodeVideoKHR)load(context, "vkCmdDecodeVideoKHR"); +#endif /* defined(VK_KHR_video_decode_queue) */ +#if defined(VK_KHR_video_encode_queue) + table->vkCmdEncodeVideoKHR = (PFN_vkCmdEncodeVideoKHR)load(context, "vkCmdEncodeVideoKHR"); + table->vkGetEncodedVideoSessionParametersKHR = (PFN_vkGetEncodedVideoSessionParametersKHR)load(context, "vkGetEncodedVideoSessionParametersKHR"); +#endif /* defined(VK_KHR_video_encode_queue) */ +#if defined(VK_KHR_video_queue) + table->vkBindVideoSessionMemoryKHR = (PFN_vkBindVideoSessionMemoryKHR)load(context, "vkBindVideoSessionMemoryKHR"); + table->vkCmdBeginVideoCodingKHR = (PFN_vkCmdBeginVideoCodingKHR)load(context, "vkCmdBeginVideoCodingKHR"); + table->vkCmdControlVideoCodingKHR = (PFN_vkCmdControlVideoCodingKHR)load(context, "vkCmdControlVideoCodingKHR"); + table->vkCmdEndVideoCodingKHR = (PFN_vkCmdEndVideoCodingKHR)load(context, "vkCmdEndVideoCodingKHR"); + table->vkCreateVideoSessionKHR = (PFN_vkCreateVideoSessionKHR)load(context, "vkCreateVideoSessionKHR"); + table->vkCreateVideoSessionParametersKHR = (PFN_vkCreateVideoSessionParametersKHR)load(context, "vkCreateVideoSessionParametersKHR"); + table->vkDestroyVideoSessionKHR = (PFN_vkDestroyVideoSessionKHR)load(context, "vkDestroyVideoSessionKHR"); + table->vkDestroyVideoSessionParametersKHR = (PFN_vkDestroyVideoSessionParametersKHR)load(context, "vkDestroyVideoSessionParametersKHR"); + table->vkGetVideoSessionMemoryRequirementsKHR = (PFN_vkGetVideoSessionMemoryRequirementsKHR)load(context, "vkGetVideoSessionMemoryRequirementsKHR"); + table->vkUpdateVideoSessionParametersKHR = (PFN_vkUpdateVideoSessionParametersKHR)load(context, "vkUpdateVideoSessionParametersKHR"); +#endif /* defined(VK_KHR_video_queue) */ +#if defined(VK_NVX_binary_import) + table->vkCmdCuLaunchKernelNVX = (PFN_vkCmdCuLaunchKernelNVX)load(context, "vkCmdCuLaunchKernelNVX"); + table->vkCreateCuFunctionNVX = (PFN_vkCreateCuFunctionNVX)load(context, "vkCreateCuFunctionNVX"); + table->vkCreateCuModuleNVX = (PFN_vkCreateCuModuleNVX)load(context, "vkCreateCuModuleNVX"); + table->vkDestroyCuFunctionNVX = (PFN_vkDestroyCuFunctionNVX)load(context, "vkDestroyCuFunctionNVX"); + table->vkDestroyCuModuleNVX = (PFN_vkDestroyCuModuleNVX)load(context, "vkDestroyCuModuleNVX"); +#endif /* defined(VK_NVX_binary_import) */ +#if defined(VK_NVX_image_view_handle) + table->vkGetImageViewHandleNVX = (PFN_vkGetImageViewHandleNVX)load(context, "vkGetImageViewHandleNVX"); +#endif /* defined(VK_NVX_image_view_handle) */ +#if defined(VK_NVX_image_view_handle) && VK_NVX_IMAGE_VIEW_HANDLE_SPEC_VERSION >= 3 + table->vkGetImageViewHandle64NVX = (PFN_vkGetImageViewHandle64NVX)load(context, "vkGetImageViewHandle64NVX"); +#endif /* defined(VK_NVX_image_view_handle) && VK_NVX_IMAGE_VIEW_HANDLE_SPEC_VERSION >= 3 */ +#if defined(VK_NVX_image_view_handle) && VK_NVX_IMAGE_VIEW_HANDLE_SPEC_VERSION >= 2 + table->vkGetImageViewAddressNVX = (PFN_vkGetImageViewAddressNVX)load(context, "vkGetImageViewAddressNVX"); +#endif /* defined(VK_NVX_image_view_handle) && VK_NVX_IMAGE_VIEW_HANDLE_SPEC_VERSION >= 2 */ +#if defined(VK_NV_clip_space_w_scaling) + table->vkCmdSetViewportWScalingNV = (PFN_vkCmdSetViewportWScalingNV)load(context, "vkCmdSetViewportWScalingNV"); +#endif /* defined(VK_NV_clip_space_w_scaling) */ +#if defined(VK_NV_copy_memory_indirect) + table->vkCmdCopyMemoryIndirectNV = (PFN_vkCmdCopyMemoryIndirectNV)load(context, "vkCmdCopyMemoryIndirectNV"); + table->vkCmdCopyMemoryToImageIndirectNV = (PFN_vkCmdCopyMemoryToImageIndirectNV)load(context, "vkCmdCopyMemoryToImageIndirectNV"); +#endif /* defined(VK_NV_copy_memory_indirect) */ +#if defined(VK_NV_cuda_kernel_launch) + table->vkCmdCudaLaunchKernelNV = (PFN_vkCmdCudaLaunchKernelNV)load(context, "vkCmdCudaLaunchKernelNV"); + table->vkCreateCudaFunctionNV = (PFN_vkCreateCudaFunctionNV)load(context, "vkCreateCudaFunctionNV"); + table->vkCreateCudaModuleNV = (PFN_vkCreateCudaModuleNV)load(context, "vkCreateCudaModuleNV"); + table->vkDestroyCudaFunctionNV = (PFN_vkDestroyCudaFunctionNV)load(context, "vkDestroyCudaFunctionNV"); + table->vkDestroyCudaModuleNV = (PFN_vkDestroyCudaModuleNV)load(context, "vkDestroyCudaModuleNV"); + table->vkGetCudaModuleCacheNV = (PFN_vkGetCudaModuleCacheNV)load(context, "vkGetCudaModuleCacheNV"); +#endif /* defined(VK_NV_cuda_kernel_launch) */ +#if defined(VK_NV_device_diagnostic_checkpoints) + table->vkCmdSetCheckpointNV = (PFN_vkCmdSetCheckpointNV)load(context, "vkCmdSetCheckpointNV"); + table->vkGetQueueCheckpointDataNV = (PFN_vkGetQueueCheckpointDataNV)load(context, "vkGetQueueCheckpointDataNV"); +#endif /* defined(VK_NV_device_diagnostic_checkpoints) */ +#if defined(VK_NV_device_diagnostic_checkpoints) && (defined(VK_VERSION_1_3) || defined(VK_KHR_synchronization2)) + table->vkGetQueueCheckpointData2NV = (PFN_vkGetQueueCheckpointData2NV)load(context, "vkGetQueueCheckpointData2NV"); +#endif /* defined(VK_NV_device_diagnostic_checkpoints) && (defined(VK_VERSION_1_3) || defined(VK_KHR_synchronization2)) */ +#if defined(VK_NV_device_generated_commands) + table->vkCmdBindPipelineShaderGroupNV = (PFN_vkCmdBindPipelineShaderGroupNV)load(context, "vkCmdBindPipelineShaderGroupNV"); + table->vkCmdExecuteGeneratedCommandsNV = (PFN_vkCmdExecuteGeneratedCommandsNV)load(context, "vkCmdExecuteGeneratedCommandsNV"); + table->vkCmdPreprocessGeneratedCommandsNV = (PFN_vkCmdPreprocessGeneratedCommandsNV)load(context, "vkCmdPreprocessGeneratedCommandsNV"); + table->vkCreateIndirectCommandsLayoutNV = (PFN_vkCreateIndirectCommandsLayoutNV)load(context, "vkCreateIndirectCommandsLayoutNV"); + table->vkDestroyIndirectCommandsLayoutNV = (PFN_vkDestroyIndirectCommandsLayoutNV)load(context, "vkDestroyIndirectCommandsLayoutNV"); + table->vkGetGeneratedCommandsMemoryRequirementsNV = (PFN_vkGetGeneratedCommandsMemoryRequirementsNV)load(context, "vkGetGeneratedCommandsMemoryRequirementsNV"); +#endif /* defined(VK_NV_device_generated_commands) */ +#if defined(VK_NV_device_generated_commands_compute) + table->vkCmdUpdatePipelineIndirectBufferNV = (PFN_vkCmdUpdatePipelineIndirectBufferNV)load(context, "vkCmdUpdatePipelineIndirectBufferNV"); + table->vkGetPipelineIndirectDeviceAddressNV = (PFN_vkGetPipelineIndirectDeviceAddressNV)load(context, "vkGetPipelineIndirectDeviceAddressNV"); + table->vkGetPipelineIndirectMemoryRequirementsNV = (PFN_vkGetPipelineIndirectMemoryRequirementsNV)load(context, "vkGetPipelineIndirectMemoryRequirementsNV"); +#endif /* defined(VK_NV_device_generated_commands_compute) */ +#if defined(VK_NV_external_memory_rdma) + table->vkGetMemoryRemoteAddressNV = (PFN_vkGetMemoryRemoteAddressNV)load(context, "vkGetMemoryRemoteAddressNV"); +#endif /* defined(VK_NV_external_memory_rdma) */ +#if defined(VK_NV_external_memory_win32) + table->vkGetMemoryWin32HandleNV = (PFN_vkGetMemoryWin32HandleNV)load(context, "vkGetMemoryWin32HandleNV"); +#endif /* defined(VK_NV_external_memory_win32) */ +#if defined(VK_NV_fragment_shading_rate_enums) + table->vkCmdSetFragmentShadingRateEnumNV = (PFN_vkCmdSetFragmentShadingRateEnumNV)load(context, "vkCmdSetFragmentShadingRateEnumNV"); +#endif /* defined(VK_NV_fragment_shading_rate_enums) */ +#if defined(VK_NV_low_latency2) + table->vkGetLatencyTimingsNV = (PFN_vkGetLatencyTimingsNV)load(context, "vkGetLatencyTimingsNV"); + table->vkLatencySleepNV = (PFN_vkLatencySleepNV)load(context, "vkLatencySleepNV"); + table->vkQueueNotifyOutOfBandNV = (PFN_vkQueueNotifyOutOfBandNV)load(context, "vkQueueNotifyOutOfBandNV"); + table->vkSetLatencyMarkerNV = (PFN_vkSetLatencyMarkerNV)load(context, "vkSetLatencyMarkerNV"); + table->vkSetLatencySleepModeNV = (PFN_vkSetLatencySleepModeNV)load(context, "vkSetLatencySleepModeNV"); +#endif /* defined(VK_NV_low_latency2) */ +#if defined(VK_NV_memory_decompression) + table->vkCmdDecompressMemoryIndirectCountNV = (PFN_vkCmdDecompressMemoryIndirectCountNV)load(context, "vkCmdDecompressMemoryIndirectCountNV"); + table->vkCmdDecompressMemoryNV = (PFN_vkCmdDecompressMemoryNV)load(context, "vkCmdDecompressMemoryNV"); +#endif /* defined(VK_NV_memory_decompression) */ +#if defined(VK_NV_mesh_shader) + table->vkCmdDrawMeshTasksIndirectNV = (PFN_vkCmdDrawMeshTasksIndirectNV)load(context, "vkCmdDrawMeshTasksIndirectNV"); + table->vkCmdDrawMeshTasksNV = (PFN_vkCmdDrawMeshTasksNV)load(context, "vkCmdDrawMeshTasksNV"); +#endif /* defined(VK_NV_mesh_shader) */ +#if defined(VK_NV_mesh_shader) && (defined(VK_KHR_draw_indirect_count) || defined(VK_VERSION_1_2)) + table->vkCmdDrawMeshTasksIndirectCountNV = (PFN_vkCmdDrawMeshTasksIndirectCountNV)load(context, "vkCmdDrawMeshTasksIndirectCountNV"); +#endif /* defined(VK_NV_mesh_shader) && (defined(VK_KHR_draw_indirect_count) || defined(VK_VERSION_1_2)) */ +#if defined(VK_NV_optical_flow) + table->vkBindOpticalFlowSessionImageNV = (PFN_vkBindOpticalFlowSessionImageNV)load(context, "vkBindOpticalFlowSessionImageNV"); + table->vkCmdOpticalFlowExecuteNV = (PFN_vkCmdOpticalFlowExecuteNV)load(context, "vkCmdOpticalFlowExecuteNV"); + table->vkCreateOpticalFlowSessionNV = (PFN_vkCreateOpticalFlowSessionNV)load(context, "vkCreateOpticalFlowSessionNV"); + table->vkDestroyOpticalFlowSessionNV = (PFN_vkDestroyOpticalFlowSessionNV)load(context, "vkDestroyOpticalFlowSessionNV"); +#endif /* defined(VK_NV_optical_flow) */ +#if defined(VK_NV_ray_tracing) + table->vkBindAccelerationStructureMemoryNV = (PFN_vkBindAccelerationStructureMemoryNV)load(context, "vkBindAccelerationStructureMemoryNV"); + table->vkCmdBuildAccelerationStructureNV = (PFN_vkCmdBuildAccelerationStructureNV)load(context, "vkCmdBuildAccelerationStructureNV"); + table->vkCmdCopyAccelerationStructureNV = (PFN_vkCmdCopyAccelerationStructureNV)load(context, "vkCmdCopyAccelerationStructureNV"); + table->vkCmdTraceRaysNV = (PFN_vkCmdTraceRaysNV)load(context, "vkCmdTraceRaysNV"); + table->vkCmdWriteAccelerationStructuresPropertiesNV = (PFN_vkCmdWriteAccelerationStructuresPropertiesNV)load(context, "vkCmdWriteAccelerationStructuresPropertiesNV"); + table->vkCompileDeferredNV = (PFN_vkCompileDeferredNV)load(context, "vkCompileDeferredNV"); + table->vkCreateAccelerationStructureNV = (PFN_vkCreateAccelerationStructureNV)load(context, "vkCreateAccelerationStructureNV"); + table->vkCreateRayTracingPipelinesNV = (PFN_vkCreateRayTracingPipelinesNV)load(context, "vkCreateRayTracingPipelinesNV"); + table->vkDestroyAccelerationStructureNV = (PFN_vkDestroyAccelerationStructureNV)load(context, "vkDestroyAccelerationStructureNV"); + table->vkGetAccelerationStructureHandleNV = (PFN_vkGetAccelerationStructureHandleNV)load(context, "vkGetAccelerationStructureHandleNV"); + table->vkGetAccelerationStructureMemoryRequirementsNV = (PFN_vkGetAccelerationStructureMemoryRequirementsNV)load(context, "vkGetAccelerationStructureMemoryRequirementsNV"); + table->vkGetRayTracingShaderGroupHandlesNV = (PFN_vkGetRayTracingShaderGroupHandlesNV)load(context, "vkGetRayTracingShaderGroupHandlesNV"); +#endif /* defined(VK_NV_ray_tracing) */ +#if defined(VK_NV_scissor_exclusive) && VK_NV_SCISSOR_EXCLUSIVE_SPEC_VERSION >= 2 + table->vkCmdSetExclusiveScissorEnableNV = (PFN_vkCmdSetExclusiveScissorEnableNV)load(context, "vkCmdSetExclusiveScissorEnableNV"); +#endif /* defined(VK_NV_scissor_exclusive) && VK_NV_SCISSOR_EXCLUSIVE_SPEC_VERSION >= 2 */ +#if defined(VK_NV_scissor_exclusive) + table->vkCmdSetExclusiveScissorNV = (PFN_vkCmdSetExclusiveScissorNV)load(context, "vkCmdSetExclusiveScissorNV"); +#endif /* defined(VK_NV_scissor_exclusive) */ +#if defined(VK_NV_shading_rate_image) + table->vkCmdBindShadingRateImageNV = (PFN_vkCmdBindShadingRateImageNV)load(context, "vkCmdBindShadingRateImageNV"); + table->vkCmdSetCoarseSampleOrderNV = (PFN_vkCmdSetCoarseSampleOrderNV)load(context, "vkCmdSetCoarseSampleOrderNV"); + table->vkCmdSetViewportShadingRatePaletteNV = (PFN_vkCmdSetViewportShadingRatePaletteNV)load(context, "vkCmdSetViewportShadingRatePaletteNV"); +#endif /* defined(VK_NV_shading_rate_image) */ +#if defined(VK_QCOM_tile_properties) + table->vkGetDynamicRenderingTilePropertiesQCOM = (PFN_vkGetDynamicRenderingTilePropertiesQCOM)load(context, "vkGetDynamicRenderingTilePropertiesQCOM"); + table->vkGetFramebufferTilePropertiesQCOM = (PFN_vkGetFramebufferTilePropertiesQCOM)load(context, "vkGetFramebufferTilePropertiesQCOM"); +#endif /* defined(VK_QCOM_tile_properties) */ +#if defined(VK_QNX_external_memory_screen_buffer) + table->vkGetScreenBufferPropertiesQNX = (PFN_vkGetScreenBufferPropertiesQNX)load(context, "vkGetScreenBufferPropertiesQNX"); +#endif /* defined(VK_QNX_external_memory_screen_buffer) */ +#if defined(VK_VALVE_descriptor_set_host_mapping) + table->vkGetDescriptorSetHostMappingVALVE = (PFN_vkGetDescriptorSetHostMappingVALVE)load(context, "vkGetDescriptorSetHostMappingVALVE"); + table->vkGetDescriptorSetLayoutHostMappingInfoVALVE = (PFN_vkGetDescriptorSetLayoutHostMappingInfoVALVE)load(context, "vkGetDescriptorSetLayoutHostMappingInfoVALVE"); +#endif /* defined(VK_VALVE_descriptor_set_host_mapping) */ +#if (defined(VK_EXT_depth_clamp_control)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_depth_clamp_control)) + table->vkCmdSetDepthClampRangeEXT = (PFN_vkCmdSetDepthClampRangeEXT)load(context, "vkCmdSetDepthClampRangeEXT"); +#endif /* (defined(VK_EXT_depth_clamp_control)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_depth_clamp_control)) */ +#if (defined(VK_EXT_extended_dynamic_state)) || (defined(VK_EXT_shader_object)) + table->vkCmdBindVertexBuffers2EXT = (PFN_vkCmdBindVertexBuffers2EXT)load(context, "vkCmdBindVertexBuffers2EXT"); + table->vkCmdSetCullModeEXT = (PFN_vkCmdSetCullModeEXT)load(context, "vkCmdSetCullModeEXT"); + table->vkCmdSetDepthBoundsTestEnableEXT = (PFN_vkCmdSetDepthBoundsTestEnableEXT)load(context, "vkCmdSetDepthBoundsTestEnableEXT"); + table->vkCmdSetDepthCompareOpEXT = (PFN_vkCmdSetDepthCompareOpEXT)load(context, "vkCmdSetDepthCompareOpEXT"); + table->vkCmdSetDepthTestEnableEXT = (PFN_vkCmdSetDepthTestEnableEXT)load(context, "vkCmdSetDepthTestEnableEXT"); + table->vkCmdSetDepthWriteEnableEXT = (PFN_vkCmdSetDepthWriteEnableEXT)load(context, "vkCmdSetDepthWriteEnableEXT"); + table->vkCmdSetFrontFaceEXT = (PFN_vkCmdSetFrontFaceEXT)load(context, "vkCmdSetFrontFaceEXT"); + table->vkCmdSetPrimitiveTopologyEXT = (PFN_vkCmdSetPrimitiveTopologyEXT)load(context, "vkCmdSetPrimitiveTopologyEXT"); + table->vkCmdSetScissorWithCountEXT = (PFN_vkCmdSetScissorWithCountEXT)load(context, "vkCmdSetScissorWithCountEXT"); + table->vkCmdSetStencilOpEXT = (PFN_vkCmdSetStencilOpEXT)load(context, "vkCmdSetStencilOpEXT"); + table->vkCmdSetStencilTestEnableEXT = (PFN_vkCmdSetStencilTestEnableEXT)load(context, "vkCmdSetStencilTestEnableEXT"); + table->vkCmdSetViewportWithCountEXT = (PFN_vkCmdSetViewportWithCountEXT)load(context, "vkCmdSetViewportWithCountEXT"); +#endif /* (defined(VK_EXT_extended_dynamic_state)) || (defined(VK_EXT_shader_object)) */ +#if (defined(VK_EXT_extended_dynamic_state2)) || (defined(VK_EXT_shader_object)) + table->vkCmdSetDepthBiasEnableEXT = (PFN_vkCmdSetDepthBiasEnableEXT)load(context, "vkCmdSetDepthBiasEnableEXT"); + table->vkCmdSetLogicOpEXT = (PFN_vkCmdSetLogicOpEXT)load(context, "vkCmdSetLogicOpEXT"); + table->vkCmdSetPatchControlPointsEXT = (PFN_vkCmdSetPatchControlPointsEXT)load(context, "vkCmdSetPatchControlPointsEXT"); + table->vkCmdSetPrimitiveRestartEnableEXT = (PFN_vkCmdSetPrimitiveRestartEnableEXT)load(context, "vkCmdSetPrimitiveRestartEnableEXT"); + table->vkCmdSetRasterizerDiscardEnableEXT = (PFN_vkCmdSetRasterizerDiscardEnableEXT)load(context, "vkCmdSetRasterizerDiscardEnableEXT"); +#endif /* (defined(VK_EXT_extended_dynamic_state2)) || (defined(VK_EXT_shader_object)) */ +#if (defined(VK_EXT_extended_dynamic_state3)) || (defined(VK_EXT_shader_object)) + table->vkCmdSetAlphaToCoverageEnableEXT = (PFN_vkCmdSetAlphaToCoverageEnableEXT)load(context, "vkCmdSetAlphaToCoverageEnableEXT"); + table->vkCmdSetAlphaToOneEnableEXT = (PFN_vkCmdSetAlphaToOneEnableEXT)load(context, "vkCmdSetAlphaToOneEnableEXT"); + table->vkCmdSetColorBlendEnableEXT = (PFN_vkCmdSetColorBlendEnableEXT)load(context, "vkCmdSetColorBlendEnableEXT"); + table->vkCmdSetColorBlendEquationEXT = (PFN_vkCmdSetColorBlendEquationEXT)load(context, "vkCmdSetColorBlendEquationEXT"); + table->vkCmdSetColorWriteMaskEXT = (PFN_vkCmdSetColorWriteMaskEXT)load(context, "vkCmdSetColorWriteMaskEXT"); + table->vkCmdSetDepthClampEnableEXT = (PFN_vkCmdSetDepthClampEnableEXT)load(context, "vkCmdSetDepthClampEnableEXT"); + table->vkCmdSetLogicOpEnableEXT = (PFN_vkCmdSetLogicOpEnableEXT)load(context, "vkCmdSetLogicOpEnableEXT"); + table->vkCmdSetPolygonModeEXT = (PFN_vkCmdSetPolygonModeEXT)load(context, "vkCmdSetPolygonModeEXT"); + table->vkCmdSetRasterizationSamplesEXT = (PFN_vkCmdSetRasterizationSamplesEXT)load(context, "vkCmdSetRasterizationSamplesEXT"); + table->vkCmdSetSampleMaskEXT = (PFN_vkCmdSetSampleMaskEXT)load(context, "vkCmdSetSampleMaskEXT"); +#endif /* (defined(VK_EXT_extended_dynamic_state3)) || (defined(VK_EXT_shader_object)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && (defined(VK_KHR_maintenance2) || defined(VK_VERSION_1_1))) || (defined(VK_EXT_shader_object)) + table->vkCmdSetTessellationDomainOriginEXT = (PFN_vkCmdSetTessellationDomainOriginEXT)load(context, "vkCmdSetTessellationDomainOriginEXT"); +#endif /* (defined(VK_EXT_extended_dynamic_state3) && (defined(VK_KHR_maintenance2) || defined(VK_VERSION_1_1))) || (defined(VK_EXT_shader_object)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_transform_feedback)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_transform_feedback)) + table->vkCmdSetRasterizationStreamEXT = (PFN_vkCmdSetRasterizationStreamEXT)load(context, "vkCmdSetRasterizationStreamEXT"); +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_transform_feedback)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_transform_feedback)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_conservative_rasterization)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_conservative_rasterization)) + table->vkCmdSetConservativeRasterizationModeEXT = (PFN_vkCmdSetConservativeRasterizationModeEXT)load(context, "vkCmdSetConservativeRasterizationModeEXT"); + table->vkCmdSetExtraPrimitiveOverestimationSizeEXT = (PFN_vkCmdSetExtraPrimitiveOverestimationSizeEXT)load(context, "vkCmdSetExtraPrimitiveOverestimationSizeEXT"); +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_conservative_rasterization)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_conservative_rasterization)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_depth_clip_enable)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_depth_clip_enable)) + table->vkCmdSetDepthClipEnableEXT = (PFN_vkCmdSetDepthClipEnableEXT)load(context, "vkCmdSetDepthClipEnableEXT"); +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_depth_clip_enable)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_depth_clip_enable)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_sample_locations)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_sample_locations)) + table->vkCmdSetSampleLocationsEnableEXT = (PFN_vkCmdSetSampleLocationsEnableEXT)load(context, "vkCmdSetSampleLocationsEnableEXT"); +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_sample_locations)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_sample_locations)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_blend_operation_advanced)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_blend_operation_advanced)) + table->vkCmdSetColorBlendAdvancedEXT = (PFN_vkCmdSetColorBlendAdvancedEXT)load(context, "vkCmdSetColorBlendAdvancedEXT"); +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_blend_operation_advanced)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_blend_operation_advanced)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_provoking_vertex)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_provoking_vertex)) + table->vkCmdSetProvokingVertexModeEXT = (PFN_vkCmdSetProvokingVertexModeEXT)load(context, "vkCmdSetProvokingVertexModeEXT"); +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_provoking_vertex)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_provoking_vertex)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_line_rasterization)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_line_rasterization)) + table->vkCmdSetLineRasterizationModeEXT = (PFN_vkCmdSetLineRasterizationModeEXT)load(context, "vkCmdSetLineRasterizationModeEXT"); + table->vkCmdSetLineStippleEnableEXT = (PFN_vkCmdSetLineStippleEnableEXT)load(context, "vkCmdSetLineStippleEnableEXT"); +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_line_rasterization)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_line_rasterization)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_depth_clip_control)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_depth_clip_control)) + table->vkCmdSetDepthClipNegativeOneToOneEXT = (PFN_vkCmdSetDepthClipNegativeOneToOneEXT)load(context, "vkCmdSetDepthClipNegativeOneToOneEXT"); +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_depth_clip_control)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_depth_clip_control)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_clip_space_w_scaling)) || (defined(VK_EXT_shader_object) && defined(VK_NV_clip_space_w_scaling)) + table->vkCmdSetViewportWScalingEnableNV = (PFN_vkCmdSetViewportWScalingEnableNV)load(context, "vkCmdSetViewportWScalingEnableNV"); +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_clip_space_w_scaling)) || (defined(VK_EXT_shader_object) && defined(VK_NV_clip_space_w_scaling)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_viewport_swizzle)) || (defined(VK_EXT_shader_object) && defined(VK_NV_viewport_swizzle)) + table->vkCmdSetViewportSwizzleNV = (PFN_vkCmdSetViewportSwizzleNV)load(context, "vkCmdSetViewportSwizzleNV"); +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_viewport_swizzle)) || (defined(VK_EXT_shader_object) && defined(VK_NV_viewport_swizzle)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_fragment_coverage_to_color)) || (defined(VK_EXT_shader_object) && defined(VK_NV_fragment_coverage_to_color)) + table->vkCmdSetCoverageToColorEnableNV = (PFN_vkCmdSetCoverageToColorEnableNV)load(context, "vkCmdSetCoverageToColorEnableNV"); + table->vkCmdSetCoverageToColorLocationNV = (PFN_vkCmdSetCoverageToColorLocationNV)load(context, "vkCmdSetCoverageToColorLocationNV"); +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_fragment_coverage_to_color)) || (defined(VK_EXT_shader_object) && defined(VK_NV_fragment_coverage_to_color)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_framebuffer_mixed_samples)) || (defined(VK_EXT_shader_object) && defined(VK_NV_framebuffer_mixed_samples)) + table->vkCmdSetCoverageModulationModeNV = (PFN_vkCmdSetCoverageModulationModeNV)load(context, "vkCmdSetCoverageModulationModeNV"); + table->vkCmdSetCoverageModulationTableEnableNV = (PFN_vkCmdSetCoverageModulationTableEnableNV)load(context, "vkCmdSetCoverageModulationTableEnableNV"); + table->vkCmdSetCoverageModulationTableNV = (PFN_vkCmdSetCoverageModulationTableNV)load(context, "vkCmdSetCoverageModulationTableNV"); +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_framebuffer_mixed_samples)) || (defined(VK_EXT_shader_object) && defined(VK_NV_framebuffer_mixed_samples)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_shading_rate_image)) || (defined(VK_EXT_shader_object) && defined(VK_NV_shading_rate_image)) + table->vkCmdSetShadingRateImageEnableNV = (PFN_vkCmdSetShadingRateImageEnableNV)load(context, "vkCmdSetShadingRateImageEnableNV"); +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_shading_rate_image)) || (defined(VK_EXT_shader_object) && defined(VK_NV_shading_rate_image)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_representative_fragment_test)) || (defined(VK_EXT_shader_object) && defined(VK_NV_representative_fragment_test)) + table->vkCmdSetRepresentativeFragmentTestEnableNV = (PFN_vkCmdSetRepresentativeFragmentTestEnableNV)load(context, "vkCmdSetRepresentativeFragmentTestEnableNV"); +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_representative_fragment_test)) || (defined(VK_EXT_shader_object) && defined(VK_NV_representative_fragment_test)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_coverage_reduction_mode)) || (defined(VK_EXT_shader_object) && defined(VK_NV_coverage_reduction_mode)) + table->vkCmdSetCoverageReductionModeNV = (PFN_vkCmdSetCoverageReductionModeNV)load(context, "vkCmdSetCoverageReductionModeNV"); +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_coverage_reduction_mode)) || (defined(VK_EXT_shader_object) && defined(VK_NV_coverage_reduction_mode)) */ +#if (defined(VK_EXT_host_image_copy)) || (defined(VK_EXT_image_compression_control)) + table->vkGetImageSubresourceLayout2EXT = (PFN_vkGetImageSubresourceLayout2EXT)load(context, "vkGetImageSubresourceLayout2EXT"); +#endif /* (defined(VK_EXT_host_image_copy)) || (defined(VK_EXT_image_compression_control)) */ +#if (defined(VK_EXT_shader_object)) || (defined(VK_EXT_vertex_input_dynamic_state)) + table->vkCmdSetVertexInputEXT = (PFN_vkCmdSetVertexInputEXT)load(context, "vkCmdSetVertexInputEXT"); +#endif /* (defined(VK_EXT_shader_object)) || (defined(VK_EXT_vertex_input_dynamic_state)) */ +#if (defined(VK_KHR_descriptor_update_template) && defined(VK_KHR_push_descriptor)) || (defined(VK_KHR_push_descriptor) && (defined(VK_VERSION_1_1) || defined(VK_KHR_descriptor_update_template))) + table->vkCmdPushDescriptorSetWithTemplateKHR = (PFN_vkCmdPushDescriptorSetWithTemplateKHR)load(context, "vkCmdPushDescriptorSetWithTemplateKHR"); +#endif /* (defined(VK_KHR_descriptor_update_template) && defined(VK_KHR_push_descriptor)) || (defined(VK_KHR_push_descriptor) && (defined(VK_VERSION_1_1) || defined(VK_KHR_descriptor_update_template))) */ +#if (defined(VK_KHR_device_group) && defined(VK_KHR_surface)) || (defined(VK_KHR_swapchain) && defined(VK_VERSION_1_1)) + table->vkGetDeviceGroupPresentCapabilitiesKHR = (PFN_vkGetDeviceGroupPresentCapabilitiesKHR)load(context, "vkGetDeviceGroupPresentCapabilitiesKHR"); + table->vkGetDeviceGroupSurfacePresentModesKHR = (PFN_vkGetDeviceGroupSurfacePresentModesKHR)load(context, "vkGetDeviceGroupSurfacePresentModesKHR"); +#endif /* (defined(VK_KHR_device_group) && defined(VK_KHR_surface)) || (defined(VK_KHR_swapchain) && defined(VK_VERSION_1_1)) */ +#if (defined(VK_KHR_device_group) && defined(VK_KHR_swapchain)) || (defined(VK_KHR_swapchain) && defined(VK_VERSION_1_1)) + table->vkAcquireNextImage2KHR = (PFN_vkAcquireNextImage2KHR)load(context, "vkAcquireNextImage2KHR"); +#endif /* (defined(VK_KHR_device_group) && defined(VK_KHR_swapchain)) || (defined(VK_KHR_swapchain) && defined(VK_VERSION_1_1)) */ + /* VOLK_GENERATE_LOAD_DEVICE_TABLE */ +} + +#ifdef __GNUC__ +#ifdef VOLK_DEFAULT_VISIBILITY +# pragma GCC visibility push(default) +#else +# pragma GCC visibility push(hidden) +#endif +#endif + +/* VOLK_GENERATE_PROTOTYPES_C */ +#if defined(VK_VERSION_1_0) +PFN_vkAllocateCommandBuffers vkAllocateCommandBuffers; +PFN_vkAllocateDescriptorSets vkAllocateDescriptorSets; +PFN_vkAllocateMemory vkAllocateMemory; +PFN_vkBeginCommandBuffer vkBeginCommandBuffer; +PFN_vkBindBufferMemory vkBindBufferMemory; +PFN_vkBindImageMemory vkBindImageMemory; +PFN_vkCmdBeginQuery vkCmdBeginQuery; +PFN_vkCmdBeginRenderPass vkCmdBeginRenderPass; +PFN_vkCmdBindDescriptorSets vkCmdBindDescriptorSets; +PFN_vkCmdBindIndexBuffer vkCmdBindIndexBuffer; +PFN_vkCmdBindPipeline vkCmdBindPipeline; +PFN_vkCmdBindVertexBuffers vkCmdBindVertexBuffers; +PFN_vkCmdBlitImage vkCmdBlitImage; +PFN_vkCmdClearAttachments vkCmdClearAttachments; +PFN_vkCmdClearColorImage vkCmdClearColorImage; +PFN_vkCmdClearDepthStencilImage vkCmdClearDepthStencilImage; +PFN_vkCmdCopyBuffer vkCmdCopyBuffer; +PFN_vkCmdCopyBufferToImage vkCmdCopyBufferToImage; +PFN_vkCmdCopyImage vkCmdCopyImage; +PFN_vkCmdCopyImageToBuffer vkCmdCopyImageToBuffer; +PFN_vkCmdCopyQueryPoolResults vkCmdCopyQueryPoolResults; +PFN_vkCmdDispatch vkCmdDispatch; +PFN_vkCmdDispatchIndirect vkCmdDispatchIndirect; +PFN_vkCmdDraw vkCmdDraw; +PFN_vkCmdDrawIndexed vkCmdDrawIndexed; +PFN_vkCmdDrawIndexedIndirect vkCmdDrawIndexedIndirect; +PFN_vkCmdDrawIndirect vkCmdDrawIndirect; +PFN_vkCmdEndQuery vkCmdEndQuery; +PFN_vkCmdEndRenderPass vkCmdEndRenderPass; +PFN_vkCmdExecuteCommands vkCmdExecuteCommands; +PFN_vkCmdFillBuffer vkCmdFillBuffer; +PFN_vkCmdNextSubpass vkCmdNextSubpass; +PFN_vkCmdPipelineBarrier vkCmdPipelineBarrier; +PFN_vkCmdPushConstants vkCmdPushConstants; +PFN_vkCmdResetEvent vkCmdResetEvent; +PFN_vkCmdResetQueryPool vkCmdResetQueryPool; +PFN_vkCmdResolveImage vkCmdResolveImage; +PFN_vkCmdSetBlendConstants vkCmdSetBlendConstants; +PFN_vkCmdSetDepthBias vkCmdSetDepthBias; +PFN_vkCmdSetDepthBounds vkCmdSetDepthBounds; +PFN_vkCmdSetEvent vkCmdSetEvent; +PFN_vkCmdSetLineWidth vkCmdSetLineWidth; +PFN_vkCmdSetScissor vkCmdSetScissor; +PFN_vkCmdSetStencilCompareMask vkCmdSetStencilCompareMask; +PFN_vkCmdSetStencilReference vkCmdSetStencilReference; +PFN_vkCmdSetStencilWriteMask vkCmdSetStencilWriteMask; +PFN_vkCmdSetViewport vkCmdSetViewport; +PFN_vkCmdUpdateBuffer vkCmdUpdateBuffer; +PFN_vkCmdWaitEvents vkCmdWaitEvents; +PFN_vkCmdWriteTimestamp vkCmdWriteTimestamp; +PFN_vkCreateBuffer vkCreateBuffer; +PFN_vkCreateBufferView vkCreateBufferView; +PFN_vkCreateCommandPool vkCreateCommandPool; +PFN_vkCreateComputePipelines vkCreateComputePipelines; +PFN_vkCreateDescriptorPool vkCreateDescriptorPool; +PFN_vkCreateDescriptorSetLayout vkCreateDescriptorSetLayout; +PFN_vkCreateDevice vkCreateDevice; +PFN_vkCreateEvent vkCreateEvent; +PFN_vkCreateFence vkCreateFence; +PFN_vkCreateFramebuffer vkCreateFramebuffer; +PFN_vkCreateGraphicsPipelines vkCreateGraphicsPipelines; +PFN_vkCreateImage vkCreateImage; +PFN_vkCreateImageView vkCreateImageView; +PFN_vkCreateInstance vkCreateInstance; +PFN_vkCreatePipelineCache vkCreatePipelineCache; +PFN_vkCreatePipelineLayout vkCreatePipelineLayout; +PFN_vkCreateQueryPool vkCreateQueryPool; +PFN_vkCreateRenderPass vkCreateRenderPass; +PFN_vkCreateSampler vkCreateSampler; +PFN_vkCreateSemaphore vkCreateSemaphore; +PFN_vkCreateShaderModule vkCreateShaderModule; +PFN_vkDestroyBuffer vkDestroyBuffer; +PFN_vkDestroyBufferView vkDestroyBufferView; +PFN_vkDestroyCommandPool vkDestroyCommandPool; +PFN_vkDestroyDescriptorPool vkDestroyDescriptorPool; +PFN_vkDestroyDescriptorSetLayout vkDestroyDescriptorSetLayout; +PFN_vkDestroyDevice vkDestroyDevice; +PFN_vkDestroyEvent vkDestroyEvent; +PFN_vkDestroyFence vkDestroyFence; +PFN_vkDestroyFramebuffer vkDestroyFramebuffer; +PFN_vkDestroyImage vkDestroyImage; +PFN_vkDestroyImageView vkDestroyImageView; +PFN_vkDestroyInstance vkDestroyInstance; +PFN_vkDestroyPipeline vkDestroyPipeline; +PFN_vkDestroyPipelineCache vkDestroyPipelineCache; +PFN_vkDestroyPipelineLayout vkDestroyPipelineLayout; +PFN_vkDestroyQueryPool vkDestroyQueryPool; +PFN_vkDestroyRenderPass vkDestroyRenderPass; +PFN_vkDestroySampler vkDestroySampler; +PFN_vkDestroySemaphore vkDestroySemaphore; +PFN_vkDestroyShaderModule vkDestroyShaderModule; +PFN_vkDeviceWaitIdle vkDeviceWaitIdle; +PFN_vkEndCommandBuffer vkEndCommandBuffer; +PFN_vkEnumerateDeviceExtensionProperties vkEnumerateDeviceExtensionProperties; +PFN_vkEnumerateDeviceLayerProperties vkEnumerateDeviceLayerProperties; +PFN_vkEnumerateInstanceExtensionProperties vkEnumerateInstanceExtensionProperties; +PFN_vkEnumerateInstanceLayerProperties vkEnumerateInstanceLayerProperties; +PFN_vkEnumeratePhysicalDevices vkEnumeratePhysicalDevices; +PFN_vkFlushMappedMemoryRanges vkFlushMappedMemoryRanges; +PFN_vkFreeCommandBuffers vkFreeCommandBuffers; +PFN_vkFreeDescriptorSets vkFreeDescriptorSets; +PFN_vkFreeMemory vkFreeMemory; +PFN_vkGetBufferMemoryRequirements vkGetBufferMemoryRequirements; +PFN_vkGetDeviceMemoryCommitment vkGetDeviceMemoryCommitment; +PFN_vkGetDeviceProcAddr vkGetDeviceProcAddr; +PFN_vkGetDeviceQueue vkGetDeviceQueue; +PFN_vkGetEventStatus vkGetEventStatus; +PFN_vkGetFenceStatus vkGetFenceStatus; +PFN_vkGetImageMemoryRequirements vkGetImageMemoryRequirements; +PFN_vkGetImageSparseMemoryRequirements vkGetImageSparseMemoryRequirements; +PFN_vkGetImageSubresourceLayout vkGetImageSubresourceLayout; +PFN_vkGetInstanceProcAddr vkGetInstanceProcAddr; +PFN_vkGetPhysicalDeviceFeatures vkGetPhysicalDeviceFeatures; +PFN_vkGetPhysicalDeviceFormatProperties vkGetPhysicalDeviceFormatProperties; +PFN_vkGetPhysicalDeviceImageFormatProperties vkGetPhysicalDeviceImageFormatProperties; +PFN_vkGetPhysicalDeviceMemoryProperties vkGetPhysicalDeviceMemoryProperties; +PFN_vkGetPhysicalDeviceProperties vkGetPhysicalDeviceProperties; +PFN_vkGetPhysicalDeviceQueueFamilyProperties vkGetPhysicalDeviceQueueFamilyProperties; +PFN_vkGetPhysicalDeviceSparseImageFormatProperties vkGetPhysicalDeviceSparseImageFormatProperties; +PFN_vkGetPipelineCacheData vkGetPipelineCacheData; +PFN_vkGetQueryPoolResults vkGetQueryPoolResults; +PFN_vkGetRenderAreaGranularity vkGetRenderAreaGranularity; +PFN_vkInvalidateMappedMemoryRanges vkInvalidateMappedMemoryRanges; +PFN_vkMapMemory vkMapMemory; +PFN_vkMergePipelineCaches vkMergePipelineCaches; +PFN_vkQueueBindSparse vkQueueBindSparse; +PFN_vkQueueSubmit vkQueueSubmit; +PFN_vkQueueWaitIdle vkQueueWaitIdle; +PFN_vkResetCommandBuffer vkResetCommandBuffer; +PFN_vkResetCommandPool vkResetCommandPool; +PFN_vkResetDescriptorPool vkResetDescriptorPool; +PFN_vkResetEvent vkResetEvent; +PFN_vkResetFences vkResetFences; +PFN_vkSetEvent vkSetEvent; +PFN_vkUnmapMemory vkUnmapMemory; +PFN_vkUpdateDescriptorSets vkUpdateDescriptorSets; +PFN_vkWaitForFences vkWaitForFences; +#endif /* defined(VK_VERSION_1_0) */ +#if defined(VK_VERSION_1_1) +PFN_vkBindBufferMemory2 vkBindBufferMemory2; +PFN_vkBindImageMemory2 vkBindImageMemory2; +PFN_vkCmdDispatchBase vkCmdDispatchBase; +PFN_vkCmdSetDeviceMask vkCmdSetDeviceMask; +PFN_vkCreateDescriptorUpdateTemplate vkCreateDescriptorUpdateTemplate; +PFN_vkCreateSamplerYcbcrConversion vkCreateSamplerYcbcrConversion; +PFN_vkDestroyDescriptorUpdateTemplate vkDestroyDescriptorUpdateTemplate; +PFN_vkDestroySamplerYcbcrConversion vkDestroySamplerYcbcrConversion; +PFN_vkEnumerateInstanceVersion vkEnumerateInstanceVersion; +PFN_vkEnumeratePhysicalDeviceGroups vkEnumeratePhysicalDeviceGroups; +PFN_vkGetBufferMemoryRequirements2 vkGetBufferMemoryRequirements2; +PFN_vkGetDescriptorSetLayoutSupport vkGetDescriptorSetLayoutSupport; +PFN_vkGetDeviceGroupPeerMemoryFeatures vkGetDeviceGroupPeerMemoryFeatures; +PFN_vkGetDeviceQueue2 vkGetDeviceQueue2; +PFN_vkGetImageMemoryRequirements2 vkGetImageMemoryRequirements2; +PFN_vkGetImageSparseMemoryRequirements2 vkGetImageSparseMemoryRequirements2; +PFN_vkGetPhysicalDeviceExternalBufferProperties vkGetPhysicalDeviceExternalBufferProperties; +PFN_vkGetPhysicalDeviceExternalFenceProperties vkGetPhysicalDeviceExternalFenceProperties; +PFN_vkGetPhysicalDeviceExternalSemaphoreProperties vkGetPhysicalDeviceExternalSemaphoreProperties; +PFN_vkGetPhysicalDeviceFeatures2 vkGetPhysicalDeviceFeatures2; +PFN_vkGetPhysicalDeviceFormatProperties2 vkGetPhysicalDeviceFormatProperties2; +PFN_vkGetPhysicalDeviceImageFormatProperties2 vkGetPhysicalDeviceImageFormatProperties2; +PFN_vkGetPhysicalDeviceMemoryProperties2 vkGetPhysicalDeviceMemoryProperties2; +PFN_vkGetPhysicalDeviceProperties2 vkGetPhysicalDeviceProperties2; +PFN_vkGetPhysicalDeviceQueueFamilyProperties2 vkGetPhysicalDeviceQueueFamilyProperties2; +PFN_vkGetPhysicalDeviceSparseImageFormatProperties2 vkGetPhysicalDeviceSparseImageFormatProperties2; +PFN_vkTrimCommandPool vkTrimCommandPool; +PFN_vkUpdateDescriptorSetWithTemplate vkUpdateDescriptorSetWithTemplate; +#endif /* defined(VK_VERSION_1_1) */ +#if defined(VK_VERSION_1_2) +PFN_vkCmdBeginRenderPass2 vkCmdBeginRenderPass2; +PFN_vkCmdDrawIndexedIndirectCount vkCmdDrawIndexedIndirectCount; +PFN_vkCmdDrawIndirectCount vkCmdDrawIndirectCount; +PFN_vkCmdEndRenderPass2 vkCmdEndRenderPass2; +PFN_vkCmdNextSubpass2 vkCmdNextSubpass2; +PFN_vkCreateRenderPass2 vkCreateRenderPass2; +PFN_vkGetBufferDeviceAddress vkGetBufferDeviceAddress; +PFN_vkGetBufferOpaqueCaptureAddress vkGetBufferOpaqueCaptureAddress; +PFN_vkGetDeviceMemoryOpaqueCaptureAddress vkGetDeviceMemoryOpaqueCaptureAddress; +PFN_vkGetSemaphoreCounterValue vkGetSemaphoreCounterValue; +PFN_vkResetQueryPool vkResetQueryPool; +PFN_vkSignalSemaphore vkSignalSemaphore; +PFN_vkWaitSemaphores vkWaitSemaphores; +#endif /* defined(VK_VERSION_1_2) */ +#if defined(VK_VERSION_1_3) +PFN_vkCmdBeginRendering vkCmdBeginRendering; +PFN_vkCmdBindVertexBuffers2 vkCmdBindVertexBuffers2; +PFN_vkCmdBlitImage2 vkCmdBlitImage2; +PFN_vkCmdCopyBuffer2 vkCmdCopyBuffer2; +PFN_vkCmdCopyBufferToImage2 vkCmdCopyBufferToImage2; +PFN_vkCmdCopyImage2 vkCmdCopyImage2; +PFN_vkCmdCopyImageToBuffer2 vkCmdCopyImageToBuffer2; +PFN_vkCmdEndRendering vkCmdEndRendering; +PFN_vkCmdPipelineBarrier2 vkCmdPipelineBarrier2; +PFN_vkCmdResetEvent2 vkCmdResetEvent2; +PFN_vkCmdResolveImage2 vkCmdResolveImage2; +PFN_vkCmdSetCullMode vkCmdSetCullMode; +PFN_vkCmdSetDepthBiasEnable vkCmdSetDepthBiasEnable; +PFN_vkCmdSetDepthBoundsTestEnable vkCmdSetDepthBoundsTestEnable; +PFN_vkCmdSetDepthCompareOp vkCmdSetDepthCompareOp; +PFN_vkCmdSetDepthTestEnable vkCmdSetDepthTestEnable; +PFN_vkCmdSetDepthWriteEnable vkCmdSetDepthWriteEnable; +PFN_vkCmdSetEvent2 vkCmdSetEvent2; +PFN_vkCmdSetFrontFace vkCmdSetFrontFace; +PFN_vkCmdSetPrimitiveRestartEnable vkCmdSetPrimitiveRestartEnable; +PFN_vkCmdSetPrimitiveTopology vkCmdSetPrimitiveTopology; +PFN_vkCmdSetRasterizerDiscardEnable vkCmdSetRasterizerDiscardEnable; +PFN_vkCmdSetScissorWithCount vkCmdSetScissorWithCount; +PFN_vkCmdSetStencilOp vkCmdSetStencilOp; +PFN_vkCmdSetStencilTestEnable vkCmdSetStencilTestEnable; +PFN_vkCmdSetViewportWithCount vkCmdSetViewportWithCount; +PFN_vkCmdWaitEvents2 vkCmdWaitEvents2; +PFN_vkCmdWriteTimestamp2 vkCmdWriteTimestamp2; +PFN_vkCreatePrivateDataSlot vkCreatePrivateDataSlot; +PFN_vkDestroyPrivateDataSlot vkDestroyPrivateDataSlot; +PFN_vkGetDeviceBufferMemoryRequirements vkGetDeviceBufferMemoryRequirements; +PFN_vkGetDeviceImageMemoryRequirements vkGetDeviceImageMemoryRequirements; +PFN_vkGetDeviceImageSparseMemoryRequirements vkGetDeviceImageSparseMemoryRequirements; +PFN_vkGetPhysicalDeviceToolProperties vkGetPhysicalDeviceToolProperties; +PFN_vkGetPrivateData vkGetPrivateData; +PFN_vkQueueSubmit2 vkQueueSubmit2; +PFN_vkSetPrivateData vkSetPrivateData; +#endif /* defined(VK_VERSION_1_3) */ +#if defined(VK_VERSION_1_4) +PFN_vkCmdBindDescriptorSets2 vkCmdBindDescriptorSets2; +PFN_vkCmdBindIndexBuffer2 vkCmdBindIndexBuffer2; +PFN_vkCmdPushConstants2 vkCmdPushConstants2; +PFN_vkCmdPushDescriptorSet vkCmdPushDescriptorSet; +PFN_vkCmdPushDescriptorSet2 vkCmdPushDescriptorSet2; +PFN_vkCmdPushDescriptorSetWithTemplate vkCmdPushDescriptorSetWithTemplate; +PFN_vkCmdPushDescriptorSetWithTemplate2 vkCmdPushDescriptorSetWithTemplate2; +PFN_vkCmdSetLineStipple vkCmdSetLineStipple; +PFN_vkCmdSetRenderingAttachmentLocations vkCmdSetRenderingAttachmentLocations; +PFN_vkCmdSetRenderingInputAttachmentIndices vkCmdSetRenderingInputAttachmentIndices; +PFN_vkCopyImageToImage vkCopyImageToImage; +PFN_vkCopyImageToMemory vkCopyImageToMemory; +PFN_vkCopyMemoryToImage vkCopyMemoryToImage; +PFN_vkGetDeviceImageSubresourceLayout vkGetDeviceImageSubresourceLayout; +PFN_vkGetImageSubresourceLayout2 vkGetImageSubresourceLayout2; +PFN_vkGetRenderingAreaGranularity vkGetRenderingAreaGranularity; +PFN_vkMapMemory2 vkMapMemory2; +PFN_vkTransitionImageLayout vkTransitionImageLayout; +PFN_vkUnmapMemory2 vkUnmapMemory2; +#endif /* defined(VK_VERSION_1_4) */ +#if defined(VK_AMDX_shader_enqueue) +PFN_vkCmdDispatchGraphAMDX vkCmdDispatchGraphAMDX; +PFN_vkCmdDispatchGraphIndirectAMDX vkCmdDispatchGraphIndirectAMDX; +PFN_vkCmdDispatchGraphIndirectCountAMDX vkCmdDispatchGraphIndirectCountAMDX; +PFN_vkCmdInitializeGraphScratchMemoryAMDX vkCmdInitializeGraphScratchMemoryAMDX; +PFN_vkCreateExecutionGraphPipelinesAMDX vkCreateExecutionGraphPipelinesAMDX; +PFN_vkGetExecutionGraphPipelineNodeIndexAMDX vkGetExecutionGraphPipelineNodeIndexAMDX; +PFN_vkGetExecutionGraphPipelineScratchSizeAMDX vkGetExecutionGraphPipelineScratchSizeAMDX; +#endif /* defined(VK_AMDX_shader_enqueue) */ +#if defined(VK_AMD_anti_lag) +PFN_vkAntiLagUpdateAMD vkAntiLagUpdateAMD; +#endif /* defined(VK_AMD_anti_lag) */ +#if defined(VK_AMD_buffer_marker) +PFN_vkCmdWriteBufferMarkerAMD vkCmdWriteBufferMarkerAMD; +#endif /* defined(VK_AMD_buffer_marker) */ +#if defined(VK_AMD_buffer_marker) && (defined(VK_VERSION_1_3) || defined(VK_KHR_synchronization2)) +PFN_vkCmdWriteBufferMarker2AMD vkCmdWriteBufferMarker2AMD; +#endif /* defined(VK_AMD_buffer_marker) && (defined(VK_VERSION_1_3) || defined(VK_KHR_synchronization2)) */ +#if defined(VK_AMD_display_native_hdr) +PFN_vkSetLocalDimmingAMD vkSetLocalDimmingAMD; +#endif /* defined(VK_AMD_display_native_hdr) */ +#if defined(VK_AMD_draw_indirect_count) +PFN_vkCmdDrawIndexedIndirectCountAMD vkCmdDrawIndexedIndirectCountAMD; +PFN_vkCmdDrawIndirectCountAMD vkCmdDrawIndirectCountAMD; +#endif /* defined(VK_AMD_draw_indirect_count) */ +#if defined(VK_AMD_shader_info) +PFN_vkGetShaderInfoAMD vkGetShaderInfoAMD; +#endif /* defined(VK_AMD_shader_info) */ +#if defined(VK_ANDROID_external_memory_android_hardware_buffer) +PFN_vkGetAndroidHardwareBufferPropertiesANDROID vkGetAndroidHardwareBufferPropertiesANDROID; +PFN_vkGetMemoryAndroidHardwareBufferANDROID vkGetMemoryAndroidHardwareBufferANDROID; +#endif /* defined(VK_ANDROID_external_memory_android_hardware_buffer) */ +#if defined(VK_EXT_acquire_drm_display) +PFN_vkAcquireDrmDisplayEXT vkAcquireDrmDisplayEXT; +PFN_vkGetDrmDisplayEXT vkGetDrmDisplayEXT; +#endif /* defined(VK_EXT_acquire_drm_display) */ +#if defined(VK_EXT_acquire_xlib_display) +PFN_vkAcquireXlibDisplayEXT vkAcquireXlibDisplayEXT; +PFN_vkGetRandROutputDisplayEXT vkGetRandROutputDisplayEXT; +#endif /* defined(VK_EXT_acquire_xlib_display) */ +#if defined(VK_EXT_attachment_feedback_loop_dynamic_state) +PFN_vkCmdSetAttachmentFeedbackLoopEnableEXT vkCmdSetAttachmentFeedbackLoopEnableEXT; +#endif /* defined(VK_EXT_attachment_feedback_loop_dynamic_state) */ +#if defined(VK_EXT_buffer_device_address) +PFN_vkGetBufferDeviceAddressEXT vkGetBufferDeviceAddressEXT; +#endif /* defined(VK_EXT_buffer_device_address) */ +#if defined(VK_EXT_calibrated_timestamps) +PFN_vkGetCalibratedTimestampsEXT vkGetCalibratedTimestampsEXT; +PFN_vkGetPhysicalDeviceCalibrateableTimeDomainsEXT vkGetPhysicalDeviceCalibrateableTimeDomainsEXT; +#endif /* defined(VK_EXT_calibrated_timestamps) */ +#if defined(VK_EXT_color_write_enable) +PFN_vkCmdSetColorWriteEnableEXT vkCmdSetColorWriteEnableEXT; +#endif /* defined(VK_EXT_color_write_enable) */ +#if defined(VK_EXT_conditional_rendering) +PFN_vkCmdBeginConditionalRenderingEXT vkCmdBeginConditionalRenderingEXT; +PFN_vkCmdEndConditionalRenderingEXT vkCmdEndConditionalRenderingEXT; +#endif /* defined(VK_EXT_conditional_rendering) */ +#if defined(VK_EXT_debug_marker) +PFN_vkCmdDebugMarkerBeginEXT vkCmdDebugMarkerBeginEXT; +PFN_vkCmdDebugMarkerEndEXT vkCmdDebugMarkerEndEXT; +PFN_vkCmdDebugMarkerInsertEXT vkCmdDebugMarkerInsertEXT; +PFN_vkDebugMarkerSetObjectNameEXT vkDebugMarkerSetObjectNameEXT; +PFN_vkDebugMarkerSetObjectTagEXT vkDebugMarkerSetObjectTagEXT; +#endif /* defined(VK_EXT_debug_marker) */ +#if defined(VK_EXT_debug_report) +PFN_vkCreateDebugReportCallbackEXT vkCreateDebugReportCallbackEXT; +PFN_vkDebugReportMessageEXT vkDebugReportMessageEXT; +PFN_vkDestroyDebugReportCallbackEXT vkDestroyDebugReportCallbackEXT; +#endif /* defined(VK_EXT_debug_report) */ +#if defined(VK_EXT_debug_utils) +PFN_vkCmdBeginDebugUtilsLabelEXT vkCmdBeginDebugUtilsLabelEXT; +PFN_vkCmdEndDebugUtilsLabelEXT vkCmdEndDebugUtilsLabelEXT; +PFN_vkCmdInsertDebugUtilsLabelEXT vkCmdInsertDebugUtilsLabelEXT; +PFN_vkCreateDebugUtilsMessengerEXT vkCreateDebugUtilsMessengerEXT; +PFN_vkDestroyDebugUtilsMessengerEXT vkDestroyDebugUtilsMessengerEXT; +PFN_vkQueueBeginDebugUtilsLabelEXT vkQueueBeginDebugUtilsLabelEXT; +PFN_vkQueueEndDebugUtilsLabelEXT vkQueueEndDebugUtilsLabelEXT; +PFN_vkQueueInsertDebugUtilsLabelEXT vkQueueInsertDebugUtilsLabelEXT; +PFN_vkSetDebugUtilsObjectNameEXT vkSetDebugUtilsObjectNameEXT; +PFN_vkSetDebugUtilsObjectTagEXT vkSetDebugUtilsObjectTagEXT; +PFN_vkSubmitDebugUtilsMessageEXT vkSubmitDebugUtilsMessageEXT; +#endif /* defined(VK_EXT_debug_utils) */ +#if defined(VK_EXT_depth_bias_control) +PFN_vkCmdSetDepthBias2EXT vkCmdSetDepthBias2EXT; +#endif /* defined(VK_EXT_depth_bias_control) */ +#if defined(VK_EXT_descriptor_buffer) +PFN_vkCmdBindDescriptorBufferEmbeddedSamplersEXT vkCmdBindDescriptorBufferEmbeddedSamplersEXT; +PFN_vkCmdBindDescriptorBuffersEXT vkCmdBindDescriptorBuffersEXT; +PFN_vkCmdSetDescriptorBufferOffsetsEXT vkCmdSetDescriptorBufferOffsetsEXT; +PFN_vkGetBufferOpaqueCaptureDescriptorDataEXT vkGetBufferOpaqueCaptureDescriptorDataEXT; +PFN_vkGetDescriptorEXT vkGetDescriptorEXT; +PFN_vkGetDescriptorSetLayoutBindingOffsetEXT vkGetDescriptorSetLayoutBindingOffsetEXT; +PFN_vkGetDescriptorSetLayoutSizeEXT vkGetDescriptorSetLayoutSizeEXT; +PFN_vkGetImageOpaqueCaptureDescriptorDataEXT vkGetImageOpaqueCaptureDescriptorDataEXT; +PFN_vkGetImageViewOpaqueCaptureDescriptorDataEXT vkGetImageViewOpaqueCaptureDescriptorDataEXT; +PFN_vkGetSamplerOpaqueCaptureDescriptorDataEXT vkGetSamplerOpaqueCaptureDescriptorDataEXT; +#endif /* defined(VK_EXT_descriptor_buffer) */ +#if defined(VK_EXT_descriptor_buffer) && (defined(VK_KHR_acceleration_structure) || defined(VK_NV_ray_tracing)) +PFN_vkGetAccelerationStructureOpaqueCaptureDescriptorDataEXT vkGetAccelerationStructureOpaqueCaptureDescriptorDataEXT; +#endif /* defined(VK_EXT_descriptor_buffer) && (defined(VK_KHR_acceleration_structure) || defined(VK_NV_ray_tracing)) */ +#if defined(VK_EXT_device_fault) +PFN_vkGetDeviceFaultInfoEXT vkGetDeviceFaultInfoEXT; +#endif /* defined(VK_EXT_device_fault) */ +#if defined(VK_EXT_device_generated_commands) +PFN_vkCmdExecuteGeneratedCommandsEXT vkCmdExecuteGeneratedCommandsEXT; +PFN_vkCmdPreprocessGeneratedCommandsEXT vkCmdPreprocessGeneratedCommandsEXT; +PFN_vkCreateIndirectCommandsLayoutEXT vkCreateIndirectCommandsLayoutEXT; +PFN_vkCreateIndirectExecutionSetEXT vkCreateIndirectExecutionSetEXT; +PFN_vkDestroyIndirectCommandsLayoutEXT vkDestroyIndirectCommandsLayoutEXT; +PFN_vkDestroyIndirectExecutionSetEXT vkDestroyIndirectExecutionSetEXT; +PFN_vkGetGeneratedCommandsMemoryRequirementsEXT vkGetGeneratedCommandsMemoryRequirementsEXT; +PFN_vkUpdateIndirectExecutionSetPipelineEXT vkUpdateIndirectExecutionSetPipelineEXT; +PFN_vkUpdateIndirectExecutionSetShaderEXT vkUpdateIndirectExecutionSetShaderEXT; +#endif /* defined(VK_EXT_device_generated_commands) */ +#if defined(VK_EXT_direct_mode_display) +PFN_vkReleaseDisplayEXT vkReleaseDisplayEXT; +#endif /* defined(VK_EXT_direct_mode_display) */ +#if defined(VK_EXT_directfb_surface) +PFN_vkCreateDirectFBSurfaceEXT vkCreateDirectFBSurfaceEXT; +PFN_vkGetPhysicalDeviceDirectFBPresentationSupportEXT vkGetPhysicalDeviceDirectFBPresentationSupportEXT; +#endif /* defined(VK_EXT_directfb_surface) */ +#if defined(VK_EXT_discard_rectangles) +PFN_vkCmdSetDiscardRectangleEXT vkCmdSetDiscardRectangleEXT; +#endif /* defined(VK_EXT_discard_rectangles) */ +#if defined(VK_EXT_discard_rectangles) && VK_EXT_DISCARD_RECTANGLES_SPEC_VERSION >= 2 +PFN_vkCmdSetDiscardRectangleEnableEXT vkCmdSetDiscardRectangleEnableEXT; +PFN_vkCmdSetDiscardRectangleModeEXT vkCmdSetDiscardRectangleModeEXT; +#endif /* defined(VK_EXT_discard_rectangles) && VK_EXT_DISCARD_RECTANGLES_SPEC_VERSION >= 2 */ +#if defined(VK_EXT_display_control) +PFN_vkDisplayPowerControlEXT vkDisplayPowerControlEXT; +PFN_vkGetSwapchainCounterEXT vkGetSwapchainCounterEXT; +PFN_vkRegisterDeviceEventEXT vkRegisterDeviceEventEXT; +PFN_vkRegisterDisplayEventEXT vkRegisterDisplayEventEXT; +#endif /* defined(VK_EXT_display_control) */ +#if defined(VK_EXT_display_surface_counter) +PFN_vkGetPhysicalDeviceSurfaceCapabilities2EXT vkGetPhysicalDeviceSurfaceCapabilities2EXT; +#endif /* defined(VK_EXT_display_surface_counter) */ +#if defined(VK_EXT_external_memory_host) +PFN_vkGetMemoryHostPointerPropertiesEXT vkGetMemoryHostPointerPropertiesEXT; +#endif /* defined(VK_EXT_external_memory_host) */ +#if defined(VK_EXT_full_screen_exclusive) +PFN_vkAcquireFullScreenExclusiveModeEXT vkAcquireFullScreenExclusiveModeEXT; +PFN_vkGetPhysicalDeviceSurfacePresentModes2EXT vkGetPhysicalDeviceSurfacePresentModes2EXT; +PFN_vkReleaseFullScreenExclusiveModeEXT vkReleaseFullScreenExclusiveModeEXT; +#endif /* defined(VK_EXT_full_screen_exclusive) */ +#if defined(VK_EXT_full_screen_exclusive) && (defined(VK_KHR_device_group) || defined(VK_VERSION_1_1)) +PFN_vkGetDeviceGroupSurfacePresentModes2EXT vkGetDeviceGroupSurfacePresentModes2EXT; +#endif /* defined(VK_EXT_full_screen_exclusive) && (defined(VK_KHR_device_group) || defined(VK_VERSION_1_1)) */ +#if defined(VK_EXT_hdr_metadata) +PFN_vkSetHdrMetadataEXT vkSetHdrMetadataEXT; +#endif /* defined(VK_EXT_hdr_metadata) */ +#if defined(VK_EXT_headless_surface) +PFN_vkCreateHeadlessSurfaceEXT vkCreateHeadlessSurfaceEXT; +#endif /* defined(VK_EXT_headless_surface) */ +#if defined(VK_EXT_host_image_copy) +PFN_vkCopyImageToImageEXT vkCopyImageToImageEXT; +PFN_vkCopyImageToMemoryEXT vkCopyImageToMemoryEXT; +PFN_vkCopyMemoryToImageEXT vkCopyMemoryToImageEXT; +PFN_vkTransitionImageLayoutEXT vkTransitionImageLayoutEXT; +#endif /* defined(VK_EXT_host_image_copy) */ +#if defined(VK_EXT_host_query_reset) +PFN_vkResetQueryPoolEXT vkResetQueryPoolEXT; +#endif /* defined(VK_EXT_host_query_reset) */ +#if defined(VK_EXT_image_drm_format_modifier) +PFN_vkGetImageDrmFormatModifierPropertiesEXT vkGetImageDrmFormatModifierPropertiesEXT; +#endif /* defined(VK_EXT_image_drm_format_modifier) */ +#if defined(VK_EXT_line_rasterization) +PFN_vkCmdSetLineStippleEXT vkCmdSetLineStippleEXT; +#endif /* defined(VK_EXT_line_rasterization) */ +#if defined(VK_EXT_mesh_shader) +PFN_vkCmdDrawMeshTasksEXT vkCmdDrawMeshTasksEXT; +PFN_vkCmdDrawMeshTasksIndirectEXT vkCmdDrawMeshTasksIndirectEXT; +#endif /* defined(VK_EXT_mesh_shader) */ +#if defined(VK_EXT_mesh_shader) && (defined(VK_KHR_draw_indirect_count) || defined(VK_VERSION_1_2)) +PFN_vkCmdDrawMeshTasksIndirectCountEXT vkCmdDrawMeshTasksIndirectCountEXT; +#endif /* defined(VK_EXT_mesh_shader) && (defined(VK_KHR_draw_indirect_count) || defined(VK_VERSION_1_2)) */ +#if defined(VK_EXT_metal_objects) +PFN_vkExportMetalObjectsEXT vkExportMetalObjectsEXT; +#endif /* defined(VK_EXT_metal_objects) */ +#if defined(VK_EXT_metal_surface) +PFN_vkCreateMetalSurfaceEXT vkCreateMetalSurfaceEXT; +#endif /* defined(VK_EXT_metal_surface) */ +#if defined(VK_EXT_multi_draw) +PFN_vkCmdDrawMultiEXT vkCmdDrawMultiEXT; +PFN_vkCmdDrawMultiIndexedEXT vkCmdDrawMultiIndexedEXT; +#endif /* defined(VK_EXT_multi_draw) */ +#if defined(VK_EXT_opacity_micromap) +PFN_vkBuildMicromapsEXT vkBuildMicromapsEXT; +PFN_vkCmdBuildMicromapsEXT vkCmdBuildMicromapsEXT; +PFN_vkCmdCopyMemoryToMicromapEXT vkCmdCopyMemoryToMicromapEXT; +PFN_vkCmdCopyMicromapEXT vkCmdCopyMicromapEXT; +PFN_vkCmdCopyMicromapToMemoryEXT vkCmdCopyMicromapToMemoryEXT; +PFN_vkCmdWriteMicromapsPropertiesEXT vkCmdWriteMicromapsPropertiesEXT; +PFN_vkCopyMemoryToMicromapEXT vkCopyMemoryToMicromapEXT; +PFN_vkCopyMicromapEXT vkCopyMicromapEXT; +PFN_vkCopyMicromapToMemoryEXT vkCopyMicromapToMemoryEXT; +PFN_vkCreateMicromapEXT vkCreateMicromapEXT; +PFN_vkDestroyMicromapEXT vkDestroyMicromapEXT; +PFN_vkGetDeviceMicromapCompatibilityEXT vkGetDeviceMicromapCompatibilityEXT; +PFN_vkGetMicromapBuildSizesEXT vkGetMicromapBuildSizesEXT; +PFN_vkWriteMicromapsPropertiesEXT vkWriteMicromapsPropertiesEXT; +#endif /* defined(VK_EXT_opacity_micromap) */ +#if defined(VK_EXT_pageable_device_local_memory) +PFN_vkSetDeviceMemoryPriorityEXT vkSetDeviceMemoryPriorityEXT; +#endif /* defined(VK_EXT_pageable_device_local_memory) */ +#if defined(VK_EXT_pipeline_properties) +PFN_vkGetPipelinePropertiesEXT vkGetPipelinePropertiesEXT; +#endif /* defined(VK_EXT_pipeline_properties) */ +#if defined(VK_EXT_private_data) +PFN_vkCreatePrivateDataSlotEXT vkCreatePrivateDataSlotEXT; +PFN_vkDestroyPrivateDataSlotEXT vkDestroyPrivateDataSlotEXT; +PFN_vkGetPrivateDataEXT vkGetPrivateDataEXT; +PFN_vkSetPrivateDataEXT vkSetPrivateDataEXT; +#endif /* defined(VK_EXT_private_data) */ +#if defined(VK_EXT_sample_locations) +PFN_vkCmdSetSampleLocationsEXT vkCmdSetSampleLocationsEXT; +PFN_vkGetPhysicalDeviceMultisamplePropertiesEXT vkGetPhysicalDeviceMultisamplePropertiesEXT; +#endif /* defined(VK_EXT_sample_locations) */ +#if defined(VK_EXT_shader_module_identifier) +PFN_vkGetShaderModuleCreateInfoIdentifierEXT vkGetShaderModuleCreateInfoIdentifierEXT; +PFN_vkGetShaderModuleIdentifierEXT vkGetShaderModuleIdentifierEXT; +#endif /* defined(VK_EXT_shader_module_identifier) */ +#if defined(VK_EXT_shader_object) +PFN_vkCmdBindShadersEXT vkCmdBindShadersEXT; +PFN_vkCreateShadersEXT vkCreateShadersEXT; +PFN_vkDestroyShaderEXT vkDestroyShaderEXT; +PFN_vkGetShaderBinaryDataEXT vkGetShaderBinaryDataEXT; +#endif /* defined(VK_EXT_shader_object) */ +#if defined(VK_EXT_swapchain_maintenance1) +PFN_vkReleaseSwapchainImagesEXT vkReleaseSwapchainImagesEXT; +#endif /* defined(VK_EXT_swapchain_maintenance1) */ +#if defined(VK_EXT_tooling_info) +PFN_vkGetPhysicalDeviceToolPropertiesEXT vkGetPhysicalDeviceToolPropertiesEXT; +#endif /* defined(VK_EXT_tooling_info) */ +#if defined(VK_EXT_transform_feedback) +PFN_vkCmdBeginQueryIndexedEXT vkCmdBeginQueryIndexedEXT; +PFN_vkCmdBeginTransformFeedbackEXT vkCmdBeginTransformFeedbackEXT; +PFN_vkCmdBindTransformFeedbackBuffersEXT vkCmdBindTransformFeedbackBuffersEXT; +PFN_vkCmdDrawIndirectByteCountEXT vkCmdDrawIndirectByteCountEXT; +PFN_vkCmdEndQueryIndexedEXT vkCmdEndQueryIndexedEXT; +PFN_vkCmdEndTransformFeedbackEXT vkCmdEndTransformFeedbackEXT; +#endif /* defined(VK_EXT_transform_feedback) */ +#if defined(VK_EXT_validation_cache) +PFN_vkCreateValidationCacheEXT vkCreateValidationCacheEXT; +PFN_vkDestroyValidationCacheEXT vkDestroyValidationCacheEXT; +PFN_vkGetValidationCacheDataEXT vkGetValidationCacheDataEXT; +PFN_vkMergeValidationCachesEXT vkMergeValidationCachesEXT; +#endif /* defined(VK_EXT_validation_cache) */ +#if defined(VK_FUCHSIA_buffer_collection) +PFN_vkCreateBufferCollectionFUCHSIA vkCreateBufferCollectionFUCHSIA; +PFN_vkDestroyBufferCollectionFUCHSIA vkDestroyBufferCollectionFUCHSIA; +PFN_vkGetBufferCollectionPropertiesFUCHSIA vkGetBufferCollectionPropertiesFUCHSIA; +PFN_vkSetBufferCollectionBufferConstraintsFUCHSIA vkSetBufferCollectionBufferConstraintsFUCHSIA; +PFN_vkSetBufferCollectionImageConstraintsFUCHSIA vkSetBufferCollectionImageConstraintsFUCHSIA; +#endif /* defined(VK_FUCHSIA_buffer_collection) */ +#if defined(VK_FUCHSIA_external_memory) +PFN_vkGetMemoryZirconHandleFUCHSIA vkGetMemoryZirconHandleFUCHSIA; +PFN_vkGetMemoryZirconHandlePropertiesFUCHSIA vkGetMemoryZirconHandlePropertiesFUCHSIA; +#endif /* defined(VK_FUCHSIA_external_memory) */ +#if defined(VK_FUCHSIA_external_semaphore) +PFN_vkGetSemaphoreZirconHandleFUCHSIA vkGetSemaphoreZirconHandleFUCHSIA; +PFN_vkImportSemaphoreZirconHandleFUCHSIA vkImportSemaphoreZirconHandleFUCHSIA; +#endif /* defined(VK_FUCHSIA_external_semaphore) */ +#if defined(VK_FUCHSIA_imagepipe_surface) +PFN_vkCreateImagePipeSurfaceFUCHSIA vkCreateImagePipeSurfaceFUCHSIA; +#endif /* defined(VK_FUCHSIA_imagepipe_surface) */ +#if defined(VK_GGP_stream_descriptor_surface) +PFN_vkCreateStreamDescriptorSurfaceGGP vkCreateStreamDescriptorSurfaceGGP; +#endif /* defined(VK_GGP_stream_descriptor_surface) */ +#if defined(VK_GOOGLE_display_timing) +PFN_vkGetPastPresentationTimingGOOGLE vkGetPastPresentationTimingGOOGLE; +PFN_vkGetRefreshCycleDurationGOOGLE vkGetRefreshCycleDurationGOOGLE; +#endif /* defined(VK_GOOGLE_display_timing) */ +#if defined(VK_HUAWEI_cluster_culling_shader) +PFN_vkCmdDrawClusterHUAWEI vkCmdDrawClusterHUAWEI; +PFN_vkCmdDrawClusterIndirectHUAWEI vkCmdDrawClusterIndirectHUAWEI; +#endif /* defined(VK_HUAWEI_cluster_culling_shader) */ +#if defined(VK_HUAWEI_invocation_mask) +PFN_vkCmdBindInvocationMaskHUAWEI vkCmdBindInvocationMaskHUAWEI; +#endif /* defined(VK_HUAWEI_invocation_mask) */ +#if defined(VK_HUAWEI_subpass_shading) && VK_HUAWEI_SUBPASS_SHADING_SPEC_VERSION >= 2 +PFN_vkGetDeviceSubpassShadingMaxWorkgroupSizeHUAWEI vkGetDeviceSubpassShadingMaxWorkgroupSizeHUAWEI; +#endif /* defined(VK_HUAWEI_subpass_shading) && VK_HUAWEI_SUBPASS_SHADING_SPEC_VERSION >= 2 */ +#if defined(VK_HUAWEI_subpass_shading) +PFN_vkCmdSubpassShadingHUAWEI vkCmdSubpassShadingHUAWEI; +#endif /* defined(VK_HUAWEI_subpass_shading) */ +#if defined(VK_INTEL_performance_query) +PFN_vkAcquirePerformanceConfigurationINTEL vkAcquirePerformanceConfigurationINTEL; +PFN_vkCmdSetPerformanceMarkerINTEL vkCmdSetPerformanceMarkerINTEL; +PFN_vkCmdSetPerformanceOverrideINTEL vkCmdSetPerformanceOverrideINTEL; +PFN_vkCmdSetPerformanceStreamMarkerINTEL vkCmdSetPerformanceStreamMarkerINTEL; +PFN_vkGetPerformanceParameterINTEL vkGetPerformanceParameterINTEL; +PFN_vkInitializePerformanceApiINTEL vkInitializePerformanceApiINTEL; +PFN_vkQueueSetPerformanceConfigurationINTEL vkQueueSetPerformanceConfigurationINTEL; +PFN_vkReleasePerformanceConfigurationINTEL vkReleasePerformanceConfigurationINTEL; +PFN_vkUninitializePerformanceApiINTEL vkUninitializePerformanceApiINTEL; +#endif /* defined(VK_INTEL_performance_query) */ +#if defined(VK_KHR_acceleration_structure) +PFN_vkBuildAccelerationStructuresKHR vkBuildAccelerationStructuresKHR; +PFN_vkCmdBuildAccelerationStructuresIndirectKHR vkCmdBuildAccelerationStructuresIndirectKHR; +PFN_vkCmdBuildAccelerationStructuresKHR vkCmdBuildAccelerationStructuresKHR; +PFN_vkCmdCopyAccelerationStructureKHR vkCmdCopyAccelerationStructureKHR; +PFN_vkCmdCopyAccelerationStructureToMemoryKHR vkCmdCopyAccelerationStructureToMemoryKHR; +PFN_vkCmdCopyMemoryToAccelerationStructureKHR vkCmdCopyMemoryToAccelerationStructureKHR; +PFN_vkCmdWriteAccelerationStructuresPropertiesKHR vkCmdWriteAccelerationStructuresPropertiesKHR; +PFN_vkCopyAccelerationStructureKHR vkCopyAccelerationStructureKHR; +PFN_vkCopyAccelerationStructureToMemoryKHR vkCopyAccelerationStructureToMemoryKHR; +PFN_vkCopyMemoryToAccelerationStructureKHR vkCopyMemoryToAccelerationStructureKHR; +PFN_vkCreateAccelerationStructureKHR vkCreateAccelerationStructureKHR; +PFN_vkDestroyAccelerationStructureKHR vkDestroyAccelerationStructureKHR; +PFN_vkGetAccelerationStructureBuildSizesKHR vkGetAccelerationStructureBuildSizesKHR; +PFN_vkGetAccelerationStructureDeviceAddressKHR vkGetAccelerationStructureDeviceAddressKHR; +PFN_vkGetDeviceAccelerationStructureCompatibilityKHR vkGetDeviceAccelerationStructureCompatibilityKHR; +PFN_vkWriteAccelerationStructuresPropertiesKHR vkWriteAccelerationStructuresPropertiesKHR; +#endif /* defined(VK_KHR_acceleration_structure) */ +#if defined(VK_KHR_android_surface) +PFN_vkCreateAndroidSurfaceKHR vkCreateAndroidSurfaceKHR; +#endif /* defined(VK_KHR_android_surface) */ +#if defined(VK_KHR_bind_memory2) +PFN_vkBindBufferMemory2KHR vkBindBufferMemory2KHR; +PFN_vkBindImageMemory2KHR vkBindImageMemory2KHR; +#endif /* defined(VK_KHR_bind_memory2) */ +#if defined(VK_KHR_buffer_device_address) +PFN_vkGetBufferDeviceAddressKHR vkGetBufferDeviceAddressKHR; +PFN_vkGetBufferOpaqueCaptureAddressKHR vkGetBufferOpaqueCaptureAddressKHR; +PFN_vkGetDeviceMemoryOpaqueCaptureAddressKHR vkGetDeviceMemoryOpaqueCaptureAddressKHR; +#endif /* defined(VK_KHR_buffer_device_address) */ +#if defined(VK_KHR_calibrated_timestamps) +PFN_vkGetCalibratedTimestampsKHR vkGetCalibratedTimestampsKHR; +PFN_vkGetPhysicalDeviceCalibrateableTimeDomainsKHR vkGetPhysicalDeviceCalibrateableTimeDomainsKHR; +#endif /* defined(VK_KHR_calibrated_timestamps) */ +#if defined(VK_KHR_cooperative_matrix) +PFN_vkGetPhysicalDeviceCooperativeMatrixPropertiesKHR vkGetPhysicalDeviceCooperativeMatrixPropertiesKHR; +#endif /* defined(VK_KHR_cooperative_matrix) */ +#if defined(VK_KHR_copy_commands2) +PFN_vkCmdBlitImage2KHR vkCmdBlitImage2KHR; +PFN_vkCmdCopyBuffer2KHR vkCmdCopyBuffer2KHR; +PFN_vkCmdCopyBufferToImage2KHR vkCmdCopyBufferToImage2KHR; +PFN_vkCmdCopyImage2KHR vkCmdCopyImage2KHR; +PFN_vkCmdCopyImageToBuffer2KHR vkCmdCopyImageToBuffer2KHR; +PFN_vkCmdResolveImage2KHR vkCmdResolveImage2KHR; +#endif /* defined(VK_KHR_copy_commands2) */ +#if defined(VK_KHR_create_renderpass2) +PFN_vkCmdBeginRenderPass2KHR vkCmdBeginRenderPass2KHR; +PFN_vkCmdEndRenderPass2KHR vkCmdEndRenderPass2KHR; +PFN_vkCmdNextSubpass2KHR vkCmdNextSubpass2KHR; +PFN_vkCreateRenderPass2KHR vkCreateRenderPass2KHR; +#endif /* defined(VK_KHR_create_renderpass2) */ +#if defined(VK_KHR_deferred_host_operations) +PFN_vkCreateDeferredOperationKHR vkCreateDeferredOperationKHR; +PFN_vkDeferredOperationJoinKHR vkDeferredOperationJoinKHR; +PFN_vkDestroyDeferredOperationKHR vkDestroyDeferredOperationKHR; +PFN_vkGetDeferredOperationMaxConcurrencyKHR vkGetDeferredOperationMaxConcurrencyKHR; +PFN_vkGetDeferredOperationResultKHR vkGetDeferredOperationResultKHR; +#endif /* defined(VK_KHR_deferred_host_operations) */ +#if defined(VK_KHR_descriptor_update_template) +PFN_vkCreateDescriptorUpdateTemplateKHR vkCreateDescriptorUpdateTemplateKHR; +PFN_vkDestroyDescriptorUpdateTemplateKHR vkDestroyDescriptorUpdateTemplateKHR; +PFN_vkUpdateDescriptorSetWithTemplateKHR vkUpdateDescriptorSetWithTemplateKHR; +#endif /* defined(VK_KHR_descriptor_update_template) */ +#if defined(VK_KHR_device_group) +PFN_vkCmdDispatchBaseKHR vkCmdDispatchBaseKHR; +PFN_vkCmdSetDeviceMaskKHR vkCmdSetDeviceMaskKHR; +PFN_vkGetDeviceGroupPeerMemoryFeaturesKHR vkGetDeviceGroupPeerMemoryFeaturesKHR; +#endif /* defined(VK_KHR_device_group) */ +#if defined(VK_KHR_device_group_creation) +PFN_vkEnumeratePhysicalDeviceGroupsKHR vkEnumeratePhysicalDeviceGroupsKHR; +#endif /* defined(VK_KHR_device_group_creation) */ +#if defined(VK_KHR_display) +PFN_vkCreateDisplayModeKHR vkCreateDisplayModeKHR; +PFN_vkCreateDisplayPlaneSurfaceKHR vkCreateDisplayPlaneSurfaceKHR; +PFN_vkGetDisplayModePropertiesKHR vkGetDisplayModePropertiesKHR; +PFN_vkGetDisplayPlaneCapabilitiesKHR vkGetDisplayPlaneCapabilitiesKHR; +PFN_vkGetDisplayPlaneSupportedDisplaysKHR vkGetDisplayPlaneSupportedDisplaysKHR; +PFN_vkGetPhysicalDeviceDisplayPlanePropertiesKHR vkGetPhysicalDeviceDisplayPlanePropertiesKHR; +PFN_vkGetPhysicalDeviceDisplayPropertiesKHR vkGetPhysicalDeviceDisplayPropertiesKHR; +#endif /* defined(VK_KHR_display) */ +#if defined(VK_KHR_display_swapchain) +PFN_vkCreateSharedSwapchainsKHR vkCreateSharedSwapchainsKHR; +#endif /* defined(VK_KHR_display_swapchain) */ +#if defined(VK_KHR_draw_indirect_count) +PFN_vkCmdDrawIndexedIndirectCountKHR vkCmdDrawIndexedIndirectCountKHR; +PFN_vkCmdDrawIndirectCountKHR vkCmdDrawIndirectCountKHR; +#endif /* defined(VK_KHR_draw_indirect_count) */ +#if defined(VK_KHR_dynamic_rendering) +PFN_vkCmdBeginRenderingKHR vkCmdBeginRenderingKHR; +PFN_vkCmdEndRenderingKHR vkCmdEndRenderingKHR; +#endif /* defined(VK_KHR_dynamic_rendering) */ +#if defined(VK_KHR_dynamic_rendering_local_read) +PFN_vkCmdSetRenderingAttachmentLocationsKHR vkCmdSetRenderingAttachmentLocationsKHR; +PFN_vkCmdSetRenderingInputAttachmentIndicesKHR vkCmdSetRenderingInputAttachmentIndicesKHR; +#endif /* defined(VK_KHR_dynamic_rendering_local_read) */ +#if defined(VK_KHR_external_fence_capabilities) +PFN_vkGetPhysicalDeviceExternalFencePropertiesKHR vkGetPhysicalDeviceExternalFencePropertiesKHR; +#endif /* defined(VK_KHR_external_fence_capabilities) */ +#if defined(VK_KHR_external_fence_fd) +PFN_vkGetFenceFdKHR vkGetFenceFdKHR; +PFN_vkImportFenceFdKHR vkImportFenceFdKHR; +#endif /* defined(VK_KHR_external_fence_fd) */ +#if defined(VK_KHR_external_fence_win32) +PFN_vkGetFenceWin32HandleKHR vkGetFenceWin32HandleKHR; +PFN_vkImportFenceWin32HandleKHR vkImportFenceWin32HandleKHR; +#endif /* defined(VK_KHR_external_fence_win32) */ +#if defined(VK_KHR_external_memory_capabilities) +PFN_vkGetPhysicalDeviceExternalBufferPropertiesKHR vkGetPhysicalDeviceExternalBufferPropertiesKHR; +#endif /* defined(VK_KHR_external_memory_capabilities) */ +#if defined(VK_KHR_external_memory_fd) +PFN_vkGetMemoryFdKHR vkGetMemoryFdKHR; +PFN_vkGetMemoryFdPropertiesKHR vkGetMemoryFdPropertiesKHR; +#endif /* defined(VK_KHR_external_memory_fd) */ +#if defined(VK_KHR_external_memory_win32) +PFN_vkGetMemoryWin32HandleKHR vkGetMemoryWin32HandleKHR; +PFN_vkGetMemoryWin32HandlePropertiesKHR vkGetMemoryWin32HandlePropertiesKHR; +#endif /* defined(VK_KHR_external_memory_win32) */ +#if defined(VK_KHR_external_semaphore_capabilities) +PFN_vkGetPhysicalDeviceExternalSemaphorePropertiesKHR vkGetPhysicalDeviceExternalSemaphorePropertiesKHR; +#endif /* defined(VK_KHR_external_semaphore_capabilities) */ +#if defined(VK_KHR_external_semaphore_fd) +PFN_vkGetSemaphoreFdKHR vkGetSemaphoreFdKHR; +PFN_vkImportSemaphoreFdKHR vkImportSemaphoreFdKHR; +#endif /* defined(VK_KHR_external_semaphore_fd) */ +#if defined(VK_KHR_external_semaphore_win32) +PFN_vkGetSemaphoreWin32HandleKHR vkGetSemaphoreWin32HandleKHR; +PFN_vkImportSemaphoreWin32HandleKHR vkImportSemaphoreWin32HandleKHR; +#endif /* defined(VK_KHR_external_semaphore_win32) */ +#if defined(VK_KHR_fragment_shading_rate) +PFN_vkCmdSetFragmentShadingRateKHR vkCmdSetFragmentShadingRateKHR; +PFN_vkGetPhysicalDeviceFragmentShadingRatesKHR vkGetPhysicalDeviceFragmentShadingRatesKHR; +#endif /* defined(VK_KHR_fragment_shading_rate) */ +#if defined(VK_KHR_get_display_properties2) +PFN_vkGetDisplayModeProperties2KHR vkGetDisplayModeProperties2KHR; +PFN_vkGetDisplayPlaneCapabilities2KHR vkGetDisplayPlaneCapabilities2KHR; +PFN_vkGetPhysicalDeviceDisplayPlaneProperties2KHR vkGetPhysicalDeviceDisplayPlaneProperties2KHR; +PFN_vkGetPhysicalDeviceDisplayProperties2KHR vkGetPhysicalDeviceDisplayProperties2KHR; +#endif /* defined(VK_KHR_get_display_properties2) */ +#if defined(VK_KHR_get_memory_requirements2) +PFN_vkGetBufferMemoryRequirements2KHR vkGetBufferMemoryRequirements2KHR; +PFN_vkGetImageMemoryRequirements2KHR vkGetImageMemoryRequirements2KHR; +PFN_vkGetImageSparseMemoryRequirements2KHR vkGetImageSparseMemoryRequirements2KHR; +#endif /* defined(VK_KHR_get_memory_requirements2) */ +#if defined(VK_KHR_get_physical_device_properties2) +PFN_vkGetPhysicalDeviceFeatures2KHR vkGetPhysicalDeviceFeatures2KHR; +PFN_vkGetPhysicalDeviceFormatProperties2KHR vkGetPhysicalDeviceFormatProperties2KHR; +PFN_vkGetPhysicalDeviceImageFormatProperties2KHR vkGetPhysicalDeviceImageFormatProperties2KHR; +PFN_vkGetPhysicalDeviceMemoryProperties2KHR vkGetPhysicalDeviceMemoryProperties2KHR; +PFN_vkGetPhysicalDeviceProperties2KHR vkGetPhysicalDeviceProperties2KHR; +PFN_vkGetPhysicalDeviceQueueFamilyProperties2KHR vkGetPhysicalDeviceQueueFamilyProperties2KHR; +PFN_vkGetPhysicalDeviceSparseImageFormatProperties2KHR vkGetPhysicalDeviceSparseImageFormatProperties2KHR; +#endif /* defined(VK_KHR_get_physical_device_properties2) */ +#if defined(VK_KHR_get_surface_capabilities2) +PFN_vkGetPhysicalDeviceSurfaceCapabilities2KHR vkGetPhysicalDeviceSurfaceCapabilities2KHR; +PFN_vkGetPhysicalDeviceSurfaceFormats2KHR vkGetPhysicalDeviceSurfaceFormats2KHR; +#endif /* defined(VK_KHR_get_surface_capabilities2) */ +#if defined(VK_KHR_line_rasterization) +PFN_vkCmdSetLineStippleKHR vkCmdSetLineStippleKHR; +#endif /* defined(VK_KHR_line_rasterization) */ +#if defined(VK_KHR_maintenance1) +PFN_vkTrimCommandPoolKHR vkTrimCommandPoolKHR; +#endif /* defined(VK_KHR_maintenance1) */ +#if defined(VK_KHR_maintenance3) +PFN_vkGetDescriptorSetLayoutSupportKHR vkGetDescriptorSetLayoutSupportKHR; +#endif /* defined(VK_KHR_maintenance3) */ +#if defined(VK_KHR_maintenance4) +PFN_vkGetDeviceBufferMemoryRequirementsKHR vkGetDeviceBufferMemoryRequirementsKHR; +PFN_vkGetDeviceImageMemoryRequirementsKHR vkGetDeviceImageMemoryRequirementsKHR; +PFN_vkGetDeviceImageSparseMemoryRequirementsKHR vkGetDeviceImageSparseMemoryRequirementsKHR; +#endif /* defined(VK_KHR_maintenance4) */ +#if defined(VK_KHR_maintenance5) +PFN_vkCmdBindIndexBuffer2KHR vkCmdBindIndexBuffer2KHR; +PFN_vkGetDeviceImageSubresourceLayoutKHR vkGetDeviceImageSubresourceLayoutKHR; +PFN_vkGetImageSubresourceLayout2KHR vkGetImageSubresourceLayout2KHR; +PFN_vkGetRenderingAreaGranularityKHR vkGetRenderingAreaGranularityKHR; +#endif /* defined(VK_KHR_maintenance5) */ +#if defined(VK_KHR_maintenance6) +PFN_vkCmdBindDescriptorSets2KHR vkCmdBindDescriptorSets2KHR; +PFN_vkCmdPushConstants2KHR vkCmdPushConstants2KHR; +#endif /* defined(VK_KHR_maintenance6) */ +#if defined(VK_KHR_maintenance6) && defined(VK_KHR_push_descriptor) +PFN_vkCmdPushDescriptorSet2KHR vkCmdPushDescriptorSet2KHR; +PFN_vkCmdPushDescriptorSetWithTemplate2KHR vkCmdPushDescriptorSetWithTemplate2KHR; +#endif /* defined(VK_KHR_maintenance6) && defined(VK_KHR_push_descriptor) */ +#if defined(VK_KHR_maintenance6) && defined(VK_EXT_descriptor_buffer) +PFN_vkCmdBindDescriptorBufferEmbeddedSamplers2EXT vkCmdBindDescriptorBufferEmbeddedSamplers2EXT; +PFN_vkCmdSetDescriptorBufferOffsets2EXT vkCmdSetDescriptorBufferOffsets2EXT; +#endif /* defined(VK_KHR_maintenance6) && defined(VK_EXT_descriptor_buffer) */ +#if defined(VK_KHR_map_memory2) +PFN_vkMapMemory2KHR vkMapMemory2KHR; +PFN_vkUnmapMemory2KHR vkUnmapMemory2KHR; +#endif /* defined(VK_KHR_map_memory2) */ +#if defined(VK_KHR_performance_query) +PFN_vkAcquireProfilingLockKHR vkAcquireProfilingLockKHR; +PFN_vkEnumeratePhysicalDeviceQueueFamilyPerformanceQueryCountersKHR vkEnumeratePhysicalDeviceQueueFamilyPerformanceQueryCountersKHR; +PFN_vkGetPhysicalDeviceQueueFamilyPerformanceQueryPassesKHR vkGetPhysicalDeviceQueueFamilyPerformanceQueryPassesKHR; +PFN_vkReleaseProfilingLockKHR vkReleaseProfilingLockKHR; +#endif /* defined(VK_KHR_performance_query) */ +#if defined(VK_KHR_pipeline_binary) +PFN_vkCreatePipelineBinariesKHR vkCreatePipelineBinariesKHR; +PFN_vkDestroyPipelineBinaryKHR vkDestroyPipelineBinaryKHR; +PFN_vkGetPipelineBinaryDataKHR vkGetPipelineBinaryDataKHR; +PFN_vkGetPipelineKeyKHR vkGetPipelineKeyKHR; +PFN_vkReleaseCapturedPipelineDataKHR vkReleaseCapturedPipelineDataKHR; +#endif /* defined(VK_KHR_pipeline_binary) */ +#if defined(VK_KHR_pipeline_executable_properties) +PFN_vkGetPipelineExecutableInternalRepresentationsKHR vkGetPipelineExecutableInternalRepresentationsKHR; +PFN_vkGetPipelineExecutablePropertiesKHR vkGetPipelineExecutablePropertiesKHR; +PFN_vkGetPipelineExecutableStatisticsKHR vkGetPipelineExecutableStatisticsKHR; +#endif /* defined(VK_KHR_pipeline_executable_properties) */ +#if defined(VK_KHR_present_wait) +PFN_vkWaitForPresentKHR vkWaitForPresentKHR; +#endif /* defined(VK_KHR_present_wait) */ +#if defined(VK_KHR_push_descriptor) +PFN_vkCmdPushDescriptorSetKHR vkCmdPushDescriptorSetKHR; +#endif /* defined(VK_KHR_push_descriptor) */ +#if defined(VK_KHR_ray_tracing_maintenance1) && defined(VK_KHR_ray_tracing_pipeline) +PFN_vkCmdTraceRaysIndirect2KHR vkCmdTraceRaysIndirect2KHR; +#endif /* defined(VK_KHR_ray_tracing_maintenance1) && defined(VK_KHR_ray_tracing_pipeline) */ +#if defined(VK_KHR_ray_tracing_pipeline) +PFN_vkCmdSetRayTracingPipelineStackSizeKHR vkCmdSetRayTracingPipelineStackSizeKHR; +PFN_vkCmdTraceRaysIndirectKHR vkCmdTraceRaysIndirectKHR; +PFN_vkCmdTraceRaysKHR vkCmdTraceRaysKHR; +PFN_vkCreateRayTracingPipelinesKHR vkCreateRayTracingPipelinesKHR; +PFN_vkGetRayTracingCaptureReplayShaderGroupHandlesKHR vkGetRayTracingCaptureReplayShaderGroupHandlesKHR; +PFN_vkGetRayTracingShaderGroupHandlesKHR vkGetRayTracingShaderGroupHandlesKHR; +PFN_vkGetRayTracingShaderGroupStackSizeKHR vkGetRayTracingShaderGroupStackSizeKHR; +#endif /* defined(VK_KHR_ray_tracing_pipeline) */ +#if defined(VK_KHR_sampler_ycbcr_conversion) +PFN_vkCreateSamplerYcbcrConversionKHR vkCreateSamplerYcbcrConversionKHR; +PFN_vkDestroySamplerYcbcrConversionKHR vkDestroySamplerYcbcrConversionKHR; +#endif /* defined(VK_KHR_sampler_ycbcr_conversion) */ +#if defined(VK_KHR_shared_presentable_image) +PFN_vkGetSwapchainStatusKHR vkGetSwapchainStatusKHR; +#endif /* defined(VK_KHR_shared_presentable_image) */ +#if defined(VK_KHR_surface) +PFN_vkDestroySurfaceKHR vkDestroySurfaceKHR; +PFN_vkGetPhysicalDeviceSurfaceCapabilitiesKHR vkGetPhysicalDeviceSurfaceCapabilitiesKHR; +PFN_vkGetPhysicalDeviceSurfaceFormatsKHR vkGetPhysicalDeviceSurfaceFormatsKHR; +PFN_vkGetPhysicalDeviceSurfacePresentModesKHR vkGetPhysicalDeviceSurfacePresentModesKHR; +PFN_vkGetPhysicalDeviceSurfaceSupportKHR vkGetPhysicalDeviceSurfaceSupportKHR; +#endif /* defined(VK_KHR_surface) */ +#if defined(VK_KHR_swapchain) +PFN_vkAcquireNextImageKHR vkAcquireNextImageKHR; +PFN_vkCreateSwapchainKHR vkCreateSwapchainKHR; +PFN_vkDestroySwapchainKHR vkDestroySwapchainKHR; +PFN_vkGetSwapchainImagesKHR vkGetSwapchainImagesKHR; +PFN_vkQueuePresentKHR vkQueuePresentKHR; +#endif /* defined(VK_KHR_swapchain) */ +#if defined(VK_KHR_synchronization2) +PFN_vkCmdPipelineBarrier2KHR vkCmdPipelineBarrier2KHR; +PFN_vkCmdResetEvent2KHR vkCmdResetEvent2KHR; +PFN_vkCmdSetEvent2KHR vkCmdSetEvent2KHR; +PFN_vkCmdWaitEvents2KHR vkCmdWaitEvents2KHR; +PFN_vkCmdWriteTimestamp2KHR vkCmdWriteTimestamp2KHR; +PFN_vkQueueSubmit2KHR vkQueueSubmit2KHR; +#endif /* defined(VK_KHR_synchronization2) */ +#if defined(VK_KHR_timeline_semaphore) +PFN_vkGetSemaphoreCounterValueKHR vkGetSemaphoreCounterValueKHR; +PFN_vkSignalSemaphoreKHR vkSignalSemaphoreKHR; +PFN_vkWaitSemaphoresKHR vkWaitSemaphoresKHR; +#endif /* defined(VK_KHR_timeline_semaphore) */ +#if defined(VK_KHR_video_decode_queue) +PFN_vkCmdDecodeVideoKHR vkCmdDecodeVideoKHR; +#endif /* defined(VK_KHR_video_decode_queue) */ +#if defined(VK_KHR_video_encode_queue) +PFN_vkCmdEncodeVideoKHR vkCmdEncodeVideoKHR; +PFN_vkGetEncodedVideoSessionParametersKHR vkGetEncodedVideoSessionParametersKHR; +PFN_vkGetPhysicalDeviceVideoEncodeQualityLevelPropertiesKHR vkGetPhysicalDeviceVideoEncodeQualityLevelPropertiesKHR; +#endif /* defined(VK_KHR_video_encode_queue) */ +#if defined(VK_KHR_video_queue) +PFN_vkBindVideoSessionMemoryKHR vkBindVideoSessionMemoryKHR; +PFN_vkCmdBeginVideoCodingKHR vkCmdBeginVideoCodingKHR; +PFN_vkCmdControlVideoCodingKHR vkCmdControlVideoCodingKHR; +PFN_vkCmdEndVideoCodingKHR vkCmdEndVideoCodingKHR; +PFN_vkCreateVideoSessionKHR vkCreateVideoSessionKHR; +PFN_vkCreateVideoSessionParametersKHR vkCreateVideoSessionParametersKHR; +PFN_vkDestroyVideoSessionKHR vkDestroyVideoSessionKHR; +PFN_vkDestroyVideoSessionParametersKHR vkDestroyVideoSessionParametersKHR; +PFN_vkGetPhysicalDeviceVideoCapabilitiesKHR vkGetPhysicalDeviceVideoCapabilitiesKHR; +PFN_vkGetPhysicalDeviceVideoFormatPropertiesKHR vkGetPhysicalDeviceVideoFormatPropertiesKHR; +PFN_vkGetVideoSessionMemoryRequirementsKHR vkGetVideoSessionMemoryRequirementsKHR; +PFN_vkUpdateVideoSessionParametersKHR vkUpdateVideoSessionParametersKHR; +#endif /* defined(VK_KHR_video_queue) */ +#if defined(VK_KHR_wayland_surface) +PFN_vkCreateWaylandSurfaceKHR vkCreateWaylandSurfaceKHR; +PFN_vkGetPhysicalDeviceWaylandPresentationSupportKHR vkGetPhysicalDeviceWaylandPresentationSupportKHR; +#endif /* defined(VK_KHR_wayland_surface) */ +#if defined(VK_KHR_win32_surface) +PFN_vkCreateWin32SurfaceKHR vkCreateWin32SurfaceKHR; +PFN_vkGetPhysicalDeviceWin32PresentationSupportKHR vkGetPhysicalDeviceWin32PresentationSupportKHR; +#endif /* defined(VK_KHR_win32_surface) */ +#if defined(VK_KHR_xcb_surface) +PFN_vkCreateXcbSurfaceKHR vkCreateXcbSurfaceKHR; +PFN_vkGetPhysicalDeviceXcbPresentationSupportKHR vkGetPhysicalDeviceXcbPresentationSupportKHR; +#endif /* defined(VK_KHR_xcb_surface) */ +#if defined(VK_KHR_xlib_surface) +PFN_vkCreateXlibSurfaceKHR vkCreateXlibSurfaceKHR; +PFN_vkGetPhysicalDeviceXlibPresentationSupportKHR vkGetPhysicalDeviceXlibPresentationSupportKHR; +#endif /* defined(VK_KHR_xlib_surface) */ +#if defined(VK_MVK_ios_surface) +PFN_vkCreateIOSSurfaceMVK vkCreateIOSSurfaceMVK; +#endif /* defined(VK_MVK_ios_surface) */ +#if defined(VK_MVK_macos_surface) +PFN_vkCreateMacOSSurfaceMVK vkCreateMacOSSurfaceMVK; +#endif /* defined(VK_MVK_macos_surface) */ +#if defined(VK_NN_vi_surface) +PFN_vkCreateViSurfaceNN vkCreateViSurfaceNN; +#endif /* defined(VK_NN_vi_surface) */ +#if defined(VK_NVX_binary_import) +PFN_vkCmdCuLaunchKernelNVX vkCmdCuLaunchKernelNVX; +PFN_vkCreateCuFunctionNVX vkCreateCuFunctionNVX; +PFN_vkCreateCuModuleNVX vkCreateCuModuleNVX; +PFN_vkDestroyCuFunctionNVX vkDestroyCuFunctionNVX; +PFN_vkDestroyCuModuleNVX vkDestroyCuModuleNVX; +#endif /* defined(VK_NVX_binary_import) */ +#if defined(VK_NVX_image_view_handle) +PFN_vkGetImageViewHandleNVX vkGetImageViewHandleNVX; +#endif /* defined(VK_NVX_image_view_handle) */ +#if defined(VK_NVX_image_view_handle) && VK_NVX_IMAGE_VIEW_HANDLE_SPEC_VERSION >= 3 +PFN_vkGetImageViewHandle64NVX vkGetImageViewHandle64NVX; +#endif /* defined(VK_NVX_image_view_handle) && VK_NVX_IMAGE_VIEW_HANDLE_SPEC_VERSION >= 3 */ +#if defined(VK_NVX_image_view_handle) && VK_NVX_IMAGE_VIEW_HANDLE_SPEC_VERSION >= 2 +PFN_vkGetImageViewAddressNVX vkGetImageViewAddressNVX; +#endif /* defined(VK_NVX_image_view_handle) && VK_NVX_IMAGE_VIEW_HANDLE_SPEC_VERSION >= 2 */ +#if defined(VK_NV_acquire_winrt_display) +PFN_vkAcquireWinrtDisplayNV vkAcquireWinrtDisplayNV; +PFN_vkGetWinrtDisplayNV vkGetWinrtDisplayNV; +#endif /* defined(VK_NV_acquire_winrt_display) */ +#if defined(VK_NV_clip_space_w_scaling) +PFN_vkCmdSetViewportWScalingNV vkCmdSetViewportWScalingNV; +#endif /* defined(VK_NV_clip_space_w_scaling) */ +#if defined(VK_NV_cooperative_matrix) +PFN_vkGetPhysicalDeviceCooperativeMatrixPropertiesNV vkGetPhysicalDeviceCooperativeMatrixPropertiesNV; +#endif /* defined(VK_NV_cooperative_matrix) */ +#if defined(VK_NV_cooperative_matrix2) +PFN_vkGetPhysicalDeviceCooperativeMatrixFlexibleDimensionsPropertiesNV vkGetPhysicalDeviceCooperativeMatrixFlexibleDimensionsPropertiesNV; +#endif /* defined(VK_NV_cooperative_matrix2) */ +#if defined(VK_NV_copy_memory_indirect) +PFN_vkCmdCopyMemoryIndirectNV vkCmdCopyMemoryIndirectNV; +PFN_vkCmdCopyMemoryToImageIndirectNV vkCmdCopyMemoryToImageIndirectNV; +#endif /* defined(VK_NV_copy_memory_indirect) */ +#if defined(VK_NV_coverage_reduction_mode) +PFN_vkGetPhysicalDeviceSupportedFramebufferMixedSamplesCombinationsNV vkGetPhysicalDeviceSupportedFramebufferMixedSamplesCombinationsNV; +#endif /* defined(VK_NV_coverage_reduction_mode) */ +#if defined(VK_NV_cuda_kernel_launch) +PFN_vkCmdCudaLaunchKernelNV vkCmdCudaLaunchKernelNV; +PFN_vkCreateCudaFunctionNV vkCreateCudaFunctionNV; +PFN_vkCreateCudaModuleNV vkCreateCudaModuleNV; +PFN_vkDestroyCudaFunctionNV vkDestroyCudaFunctionNV; +PFN_vkDestroyCudaModuleNV vkDestroyCudaModuleNV; +PFN_vkGetCudaModuleCacheNV vkGetCudaModuleCacheNV; +#endif /* defined(VK_NV_cuda_kernel_launch) */ +#if defined(VK_NV_device_diagnostic_checkpoints) +PFN_vkCmdSetCheckpointNV vkCmdSetCheckpointNV; +PFN_vkGetQueueCheckpointDataNV vkGetQueueCheckpointDataNV; +#endif /* defined(VK_NV_device_diagnostic_checkpoints) */ +#if defined(VK_NV_device_diagnostic_checkpoints) && (defined(VK_VERSION_1_3) || defined(VK_KHR_synchronization2)) +PFN_vkGetQueueCheckpointData2NV vkGetQueueCheckpointData2NV; +#endif /* defined(VK_NV_device_diagnostic_checkpoints) && (defined(VK_VERSION_1_3) || defined(VK_KHR_synchronization2)) */ +#if defined(VK_NV_device_generated_commands) +PFN_vkCmdBindPipelineShaderGroupNV vkCmdBindPipelineShaderGroupNV; +PFN_vkCmdExecuteGeneratedCommandsNV vkCmdExecuteGeneratedCommandsNV; +PFN_vkCmdPreprocessGeneratedCommandsNV vkCmdPreprocessGeneratedCommandsNV; +PFN_vkCreateIndirectCommandsLayoutNV vkCreateIndirectCommandsLayoutNV; +PFN_vkDestroyIndirectCommandsLayoutNV vkDestroyIndirectCommandsLayoutNV; +PFN_vkGetGeneratedCommandsMemoryRequirementsNV vkGetGeneratedCommandsMemoryRequirementsNV; +#endif /* defined(VK_NV_device_generated_commands) */ +#if defined(VK_NV_device_generated_commands_compute) +PFN_vkCmdUpdatePipelineIndirectBufferNV vkCmdUpdatePipelineIndirectBufferNV; +PFN_vkGetPipelineIndirectDeviceAddressNV vkGetPipelineIndirectDeviceAddressNV; +PFN_vkGetPipelineIndirectMemoryRequirementsNV vkGetPipelineIndirectMemoryRequirementsNV; +#endif /* defined(VK_NV_device_generated_commands_compute) */ +#if defined(VK_NV_external_memory_capabilities) +PFN_vkGetPhysicalDeviceExternalImageFormatPropertiesNV vkGetPhysicalDeviceExternalImageFormatPropertiesNV; +#endif /* defined(VK_NV_external_memory_capabilities) */ +#if defined(VK_NV_external_memory_rdma) +PFN_vkGetMemoryRemoteAddressNV vkGetMemoryRemoteAddressNV; +#endif /* defined(VK_NV_external_memory_rdma) */ +#if defined(VK_NV_external_memory_win32) +PFN_vkGetMemoryWin32HandleNV vkGetMemoryWin32HandleNV; +#endif /* defined(VK_NV_external_memory_win32) */ +#if defined(VK_NV_fragment_shading_rate_enums) +PFN_vkCmdSetFragmentShadingRateEnumNV vkCmdSetFragmentShadingRateEnumNV; +#endif /* defined(VK_NV_fragment_shading_rate_enums) */ +#if defined(VK_NV_low_latency2) +PFN_vkGetLatencyTimingsNV vkGetLatencyTimingsNV; +PFN_vkLatencySleepNV vkLatencySleepNV; +PFN_vkQueueNotifyOutOfBandNV vkQueueNotifyOutOfBandNV; +PFN_vkSetLatencyMarkerNV vkSetLatencyMarkerNV; +PFN_vkSetLatencySleepModeNV vkSetLatencySleepModeNV; +#endif /* defined(VK_NV_low_latency2) */ +#if defined(VK_NV_memory_decompression) +PFN_vkCmdDecompressMemoryIndirectCountNV vkCmdDecompressMemoryIndirectCountNV; +PFN_vkCmdDecompressMemoryNV vkCmdDecompressMemoryNV; +#endif /* defined(VK_NV_memory_decompression) */ +#if defined(VK_NV_mesh_shader) +PFN_vkCmdDrawMeshTasksIndirectNV vkCmdDrawMeshTasksIndirectNV; +PFN_vkCmdDrawMeshTasksNV vkCmdDrawMeshTasksNV; +#endif /* defined(VK_NV_mesh_shader) */ +#if defined(VK_NV_mesh_shader) && (defined(VK_KHR_draw_indirect_count) || defined(VK_VERSION_1_2)) +PFN_vkCmdDrawMeshTasksIndirectCountNV vkCmdDrawMeshTasksIndirectCountNV; +#endif /* defined(VK_NV_mesh_shader) && (defined(VK_KHR_draw_indirect_count) || defined(VK_VERSION_1_2)) */ +#if defined(VK_NV_optical_flow) +PFN_vkBindOpticalFlowSessionImageNV vkBindOpticalFlowSessionImageNV; +PFN_vkCmdOpticalFlowExecuteNV vkCmdOpticalFlowExecuteNV; +PFN_vkCreateOpticalFlowSessionNV vkCreateOpticalFlowSessionNV; +PFN_vkDestroyOpticalFlowSessionNV vkDestroyOpticalFlowSessionNV; +PFN_vkGetPhysicalDeviceOpticalFlowImageFormatsNV vkGetPhysicalDeviceOpticalFlowImageFormatsNV; +#endif /* defined(VK_NV_optical_flow) */ +#if defined(VK_NV_ray_tracing) +PFN_vkBindAccelerationStructureMemoryNV vkBindAccelerationStructureMemoryNV; +PFN_vkCmdBuildAccelerationStructureNV vkCmdBuildAccelerationStructureNV; +PFN_vkCmdCopyAccelerationStructureNV vkCmdCopyAccelerationStructureNV; +PFN_vkCmdTraceRaysNV vkCmdTraceRaysNV; +PFN_vkCmdWriteAccelerationStructuresPropertiesNV vkCmdWriteAccelerationStructuresPropertiesNV; +PFN_vkCompileDeferredNV vkCompileDeferredNV; +PFN_vkCreateAccelerationStructureNV vkCreateAccelerationStructureNV; +PFN_vkCreateRayTracingPipelinesNV vkCreateRayTracingPipelinesNV; +PFN_vkDestroyAccelerationStructureNV vkDestroyAccelerationStructureNV; +PFN_vkGetAccelerationStructureHandleNV vkGetAccelerationStructureHandleNV; +PFN_vkGetAccelerationStructureMemoryRequirementsNV vkGetAccelerationStructureMemoryRequirementsNV; +PFN_vkGetRayTracingShaderGroupHandlesNV vkGetRayTracingShaderGroupHandlesNV; +#endif /* defined(VK_NV_ray_tracing) */ +#if defined(VK_NV_scissor_exclusive) && VK_NV_SCISSOR_EXCLUSIVE_SPEC_VERSION >= 2 +PFN_vkCmdSetExclusiveScissorEnableNV vkCmdSetExclusiveScissorEnableNV; +#endif /* defined(VK_NV_scissor_exclusive) && VK_NV_SCISSOR_EXCLUSIVE_SPEC_VERSION >= 2 */ +#if defined(VK_NV_scissor_exclusive) +PFN_vkCmdSetExclusiveScissorNV vkCmdSetExclusiveScissorNV; +#endif /* defined(VK_NV_scissor_exclusive) */ +#if defined(VK_NV_shading_rate_image) +PFN_vkCmdBindShadingRateImageNV vkCmdBindShadingRateImageNV; +PFN_vkCmdSetCoarseSampleOrderNV vkCmdSetCoarseSampleOrderNV; +PFN_vkCmdSetViewportShadingRatePaletteNV vkCmdSetViewportShadingRatePaletteNV; +#endif /* defined(VK_NV_shading_rate_image) */ +#if defined(VK_QCOM_tile_properties) +PFN_vkGetDynamicRenderingTilePropertiesQCOM vkGetDynamicRenderingTilePropertiesQCOM; +PFN_vkGetFramebufferTilePropertiesQCOM vkGetFramebufferTilePropertiesQCOM; +#endif /* defined(VK_QCOM_tile_properties) */ +#if defined(VK_QNX_external_memory_screen_buffer) +PFN_vkGetScreenBufferPropertiesQNX vkGetScreenBufferPropertiesQNX; +#endif /* defined(VK_QNX_external_memory_screen_buffer) */ +#if defined(VK_QNX_screen_surface) +PFN_vkCreateScreenSurfaceQNX vkCreateScreenSurfaceQNX; +PFN_vkGetPhysicalDeviceScreenPresentationSupportQNX vkGetPhysicalDeviceScreenPresentationSupportQNX; +#endif /* defined(VK_QNX_screen_surface) */ +#if defined(VK_VALVE_descriptor_set_host_mapping) +PFN_vkGetDescriptorSetHostMappingVALVE vkGetDescriptorSetHostMappingVALVE; +PFN_vkGetDescriptorSetLayoutHostMappingInfoVALVE vkGetDescriptorSetLayoutHostMappingInfoVALVE; +#endif /* defined(VK_VALVE_descriptor_set_host_mapping) */ +#if (defined(VK_EXT_depth_clamp_control)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_depth_clamp_control)) +PFN_vkCmdSetDepthClampRangeEXT vkCmdSetDepthClampRangeEXT; +#endif /* (defined(VK_EXT_depth_clamp_control)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_depth_clamp_control)) */ +#if (defined(VK_EXT_extended_dynamic_state)) || (defined(VK_EXT_shader_object)) +PFN_vkCmdBindVertexBuffers2EXT vkCmdBindVertexBuffers2EXT; +PFN_vkCmdSetCullModeEXT vkCmdSetCullModeEXT; +PFN_vkCmdSetDepthBoundsTestEnableEXT vkCmdSetDepthBoundsTestEnableEXT; +PFN_vkCmdSetDepthCompareOpEXT vkCmdSetDepthCompareOpEXT; +PFN_vkCmdSetDepthTestEnableEXT vkCmdSetDepthTestEnableEXT; +PFN_vkCmdSetDepthWriteEnableEXT vkCmdSetDepthWriteEnableEXT; +PFN_vkCmdSetFrontFaceEXT vkCmdSetFrontFaceEXT; +PFN_vkCmdSetPrimitiveTopologyEXT vkCmdSetPrimitiveTopologyEXT; +PFN_vkCmdSetScissorWithCountEXT vkCmdSetScissorWithCountEXT; +PFN_vkCmdSetStencilOpEXT vkCmdSetStencilOpEXT; +PFN_vkCmdSetStencilTestEnableEXT vkCmdSetStencilTestEnableEXT; +PFN_vkCmdSetViewportWithCountEXT vkCmdSetViewportWithCountEXT; +#endif /* (defined(VK_EXT_extended_dynamic_state)) || (defined(VK_EXT_shader_object)) */ +#if (defined(VK_EXT_extended_dynamic_state2)) || (defined(VK_EXT_shader_object)) +PFN_vkCmdSetDepthBiasEnableEXT vkCmdSetDepthBiasEnableEXT; +PFN_vkCmdSetLogicOpEXT vkCmdSetLogicOpEXT; +PFN_vkCmdSetPatchControlPointsEXT vkCmdSetPatchControlPointsEXT; +PFN_vkCmdSetPrimitiveRestartEnableEXT vkCmdSetPrimitiveRestartEnableEXT; +PFN_vkCmdSetRasterizerDiscardEnableEXT vkCmdSetRasterizerDiscardEnableEXT; +#endif /* (defined(VK_EXT_extended_dynamic_state2)) || (defined(VK_EXT_shader_object)) */ +#if (defined(VK_EXT_extended_dynamic_state3)) || (defined(VK_EXT_shader_object)) +PFN_vkCmdSetAlphaToCoverageEnableEXT vkCmdSetAlphaToCoverageEnableEXT; +PFN_vkCmdSetAlphaToOneEnableEXT vkCmdSetAlphaToOneEnableEXT; +PFN_vkCmdSetColorBlendEnableEXT vkCmdSetColorBlendEnableEXT; +PFN_vkCmdSetColorBlendEquationEXT vkCmdSetColorBlendEquationEXT; +PFN_vkCmdSetColorWriteMaskEXT vkCmdSetColorWriteMaskEXT; +PFN_vkCmdSetDepthClampEnableEXT vkCmdSetDepthClampEnableEXT; +PFN_vkCmdSetLogicOpEnableEXT vkCmdSetLogicOpEnableEXT; +PFN_vkCmdSetPolygonModeEXT vkCmdSetPolygonModeEXT; +PFN_vkCmdSetRasterizationSamplesEXT vkCmdSetRasterizationSamplesEXT; +PFN_vkCmdSetSampleMaskEXT vkCmdSetSampleMaskEXT; +#endif /* (defined(VK_EXT_extended_dynamic_state3)) || (defined(VK_EXT_shader_object)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && (defined(VK_KHR_maintenance2) || defined(VK_VERSION_1_1))) || (defined(VK_EXT_shader_object)) +PFN_vkCmdSetTessellationDomainOriginEXT vkCmdSetTessellationDomainOriginEXT; +#endif /* (defined(VK_EXT_extended_dynamic_state3) && (defined(VK_KHR_maintenance2) || defined(VK_VERSION_1_1))) || (defined(VK_EXT_shader_object)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_transform_feedback)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_transform_feedback)) +PFN_vkCmdSetRasterizationStreamEXT vkCmdSetRasterizationStreamEXT; +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_transform_feedback)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_transform_feedback)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_conservative_rasterization)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_conservative_rasterization)) +PFN_vkCmdSetConservativeRasterizationModeEXT vkCmdSetConservativeRasterizationModeEXT; +PFN_vkCmdSetExtraPrimitiveOverestimationSizeEXT vkCmdSetExtraPrimitiveOverestimationSizeEXT; +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_conservative_rasterization)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_conservative_rasterization)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_depth_clip_enable)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_depth_clip_enable)) +PFN_vkCmdSetDepthClipEnableEXT vkCmdSetDepthClipEnableEXT; +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_depth_clip_enable)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_depth_clip_enable)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_sample_locations)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_sample_locations)) +PFN_vkCmdSetSampleLocationsEnableEXT vkCmdSetSampleLocationsEnableEXT; +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_sample_locations)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_sample_locations)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_blend_operation_advanced)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_blend_operation_advanced)) +PFN_vkCmdSetColorBlendAdvancedEXT vkCmdSetColorBlendAdvancedEXT; +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_blend_operation_advanced)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_blend_operation_advanced)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_provoking_vertex)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_provoking_vertex)) +PFN_vkCmdSetProvokingVertexModeEXT vkCmdSetProvokingVertexModeEXT; +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_provoking_vertex)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_provoking_vertex)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_line_rasterization)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_line_rasterization)) +PFN_vkCmdSetLineRasterizationModeEXT vkCmdSetLineRasterizationModeEXT; +PFN_vkCmdSetLineStippleEnableEXT vkCmdSetLineStippleEnableEXT; +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_line_rasterization)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_line_rasterization)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_depth_clip_control)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_depth_clip_control)) +PFN_vkCmdSetDepthClipNegativeOneToOneEXT vkCmdSetDepthClipNegativeOneToOneEXT; +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_EXT_depth_clip_control)) || (defined(VK_EXT_shader_object) && defined(VK_EXT_depth_clip_control)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_clip_space_w_scaling)) || (defined(VK_EXT_shader_object) && defined(VK_NV_clip_space_w_scaling)) +PFN_vkCmdSetViewportWScalingEnableNV vkCmdSetViewportWScalingEnableNV; +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_clip_space_w_scaling)) || (defined(VK_EXT_shader_object) && defined(VK_NV_clip_space_w_scaling)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_viewport_swizzle)) || (defined(VK_EXT_shader_object) && defined(VK_NV_viewport_swizzle)) +PFN_vkCmdSetViewportSwizzleNV vkCmdSetViewportSwizzleNV; +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_viewport_swizzle)) || (defined(VK_EXT_shader_object) && defined(VK_NV_viewport_swizzle)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_fragment_coverage_to_color)) || (defined(VK_EXT_shader_object) && defined(VK_NV_fragment_coverage_to_color)) +PFN_vkCmdSetCoverageToColorEnableNV vkCmdSetCoverageToColorEnableNV; +PFN_vkCmdSetCoverageToColorLocationNV vkCmdSetCoverageToColorLocationNV; +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_fragment_coverage_to_color)) || (defined(VK_EXT_shader_object) && defined(VK_NV_fragment_coverage_to_color)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_framebuffer_mixed_samples)) || (defined(VK_EXT_shader_object) && defined(VK_NV_framebuffer_mixed_samples)) +PFN_vkCmdSetCoverageModulationModeNV vkCmdSetCoverageModulationModeNV; +PFN_vkCmdSetCoverageModulationTableEnableNV vkCmdSetCoverageModulationTableEnableNV; +PFN_vkCmdSetCoverageModulationTableNV vkCmdSetCoverageModulationTableNV; +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_framebuffer_mixed_samples)) || (defined(VK_EXT_shader_object) && defined(VK_NV_framebuffer_mixed_samples)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_shading_rate_image)) || (defined(VK_EXT_shader_object) && defined(VK_NV_shading_rate_image)) +PFN_vkCmdSetShadingRateImageEnableNV vkCmdSetShadingRateImageEnableNV; +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_shading_rate_image)) || (defined(VK_EXT_shader_object) && defined(VK_NV_shading_rate_image)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_representative_fragment_test)) || (defined(VK_EXT_shader_object) && defined(VK_NV_representative_fragment_test)) +PFN_vkCmdSetRepresentativeFragmentTestEnableNV vkCmdSetRepresentativeFragmentTestEnableNV; +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_representative_fragment_test)) || (defined(VK_EXT_shader_object) && defined(VK_NV_representative_fragment_test)) */ +#if (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_coverage_reduction_mode)) || (defined(VK_EXT_shader_object) && defined(VK_NV_coverage_reduction_mode)) +PFN_vkCmdSetCoverageReductionModeNV vkCmdSetCoverageReductionModeNV; +#endif /* (defined(VK_EXT_extended_dynamic_state3) && defined(VK_NV_coverage_reduction_mode)) || (defined(VK_EXT_shader_object) && defined(VK_NV_coverage_reduction_mode)) */ +#if (defined(VK_EXT_host_image_copy)) || (defined(VK_EXT_image_compression_control)) +PFN_vkGetImageSubresourceLayout2EXT vkGetImageSubresourceLayout2EXT; +#endif /* (defined(VK_EXT_host_image_copy)) || (defined(VK_EXT_image_compression_control)) */ +#if (defined(VK_EXT_shader_object)) || (defined(VK_EXT_vertex_input_dynamic_state)) +PFN_vkCmdSetVertexInputEXT vkCmdSetVertexInputEXT; +#endif /* (defined(VK_EXT_shader_object)) || (defined(VK_EXT_vertex_input_dynamic_state)) */ +#if (defined(VK_KHR_descriptor_update_template) && defined(VK_KHR_push_descriptor)) || (defined(VK_KHR_push_descriptor) && (defined(VK_VERSION_1_1) || defined(VK_KHR_descriptor_update_template))) +PFN_vkCmdPushDescriptorSetWithTemplateKHR vkCmdPushDescriptorSetWithTemplateKHR; +#endif /* (defined(VK_KHR_descriptor_update_template) && defined(VK_KHR_push_descriptor)) || (defined(VK_KHR_push_descriptor) && (defined(VK_VERSION_1_1) || defined(VK_KHR_descriptor_update_template))) */ +#if (defined(VK_KHR_device_group) && defined(VK_KHR_surface)) || (defined(VK_KHR_swapchain) && defined(VK_VERSION_1_1)) +PFN_vkGetDeviceGroupPresentCapabilitiesKHR vkGetDeviceGroupPresentCapabilitiesKHR; +PFN_vkGetDeviceGroupSurfacePresentModesKHR vkGetDeviceGroupSurfacePresentModesKHR; +PFN_vkGetPhysicalDevicePresentRectanglesKHR vkGetPhysicalDevicePresentRectanglesKHR; +#endif /* (defined(VK_KHR_device_group) && defined(VK_KHR_surface)) || (defined(VK_KHR_swapchain) && defined(VK_VERSION_1_1)) */ +#if (defined(VK_KHR_device_group) && defined(VK_KHR_swapchain)) || (defined(VK_KHR_swapchain) && defined(VK_VERSION_1_1)) +PFN_vkAcquireNextImage2KHR vkAcquireNextImage2KHR; +#endif /* (defined(VK_KHR_device_group) && defined(VK_KHR_swapchain)) || (defined(VK_KHR_swapchain) && defined(VK_VERSION_1_1)) */ +/* VOLK_GENERATE_PROTOTYPES_C */ + +#ifdef __GNUC__ +# pragma GCC visibility pop +#endif + +#ifdef __cplusplus +} +#endif +/* clang-format on */ diff --git a/source/platform/window_manager.cpp b/source/platform/window_manager.cpp index f3835c2..481895f 100644 --- a/source/platform/window_manager.cpp +++ b/source/platform/window_manager.cpp @@ -45,13 +45,13 @@ void window_manager::initialize() { // Find first valid server while (not display_servers.is_empty()) { - display_server::entry it = display_servers.front(); + const display_server::entry it = display_servers.front(); display_servers.pop(); unique_ptr server = unique_ptr(it.ctor(_platform)); server->connect(); if (server->connected()) { - logger::log(format("Selected {} for the display server.", server->get_type().name())); + logger::log(logger::info, format("Selected {} for the display server.", server->get_type().name())); _display = move(server); break; } @@ -61,7 +61,7 @@ void window_manager::initialize() { _thread = thread::current(); - logger::log(format("Initializing Window Manager on thread: {:#016x}.", _thread)); + logger::log(logger::info, format("Initializing Window Manager on thread: {:#016x}.", _thread)); } void window_manager::shutdown() { @@ -92,6 +92,11 @@ void window_manager::dispatch() { assertf(_thread == thread::current(), "Attempted to dispatch Window Manager on a different thread!"); lock_guard guard(_lock); + size_t n = _commands.size(); + while (n--) { + _commands.pop(); + } + _display->dispatch(); } @@ -104,7 +109,7 @@ window_id window_manager::create_window(const window::config& config, window_id lock_guard guard(_lock); window* p = parent == nullid ? nullptr : _windows[parent].get(); - window_id id = _windows.emplace(_display->create_window(config, p)); + const window_id id = _windows.emplace(_display->create_window(config, p)); _windows[id]->initialize(); return id; } @@ -144,11 +149,25 @@ void window_manager::close(window_id window) { _windows.erase(window); } -window_id window_manager::_parent(window_id) const { +window_id window_manager::_parent(window_id id) const { + window_id it = 0; + for (const auto& window : _windows) { + if (window.get() == _windows[id]->parent) { + return it; + } + ++it; + } return nullid; } -window_id window_manager::_root(window_id) const { +window_id window_manager::_root(window_id id) const { + window_id it = 0; + for (const auto& window : _windows) { + if (window.get() == _windows[id]->root) { + return it; + } + ++it; + } return nullid; } diff --git a/source/renderers/vulkan/vkcontext.cpp b/source/renderers/vulkan/vkcontext.cpp new file mode 100644 index 0000000..e09f868 --- /dev/null +++ b/source/renderers/vulkan/vkcontext.cpp @@ -0,0 +1,85 @@ +// ===================================================================================================================== +// fennec, a free and open source game engine +// Copyright © 2025 - 2026 Medusa Slockbower +// +// This program is free software: you can redistribute it and/or modify +// it under the terms of the GNU General Public License as published by +// the Free Software Foundation, either version 3 of the License, or +// (at your option) any later version. +// +// This program is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. +// +// You should have received a copy of the GNU General Public License +// along with this program. If not, see . +// ===================================================================================================================== + + +#include +#include + +namespace fennec { + +vkcontext::vkcontext(display_server* display, const dynarray& extensions) + : gfxcontext(display) { + + const vk::app_info app( + "", { + .major = 1, + .minor = 0, + .patch = 0, + .meta = 0 + }, + "fennec", { + .major = FENNEC_VERSION_MAJOR, + .minor = FENNEC_VERSION_MINOR, + .patch = FENNEC_VERSION_PATCH, + } + ); + + vk::instance::create_info info( + vk::instance_flag_none, app + ); + + if constexpr (FENNEC_DEBUG) { + info.enable_layer("VK_LAYER_KHRONOS_validation"); + info.enable_extension(VK_EXT_DEBUG_UTILS_EXTENSION_NAME); + + info.attach_debugger(*this); + } + + for (const cstring& ext : extensions) { + info.enable_extension(ext); + } + + instance = make_unique(info); +} + +vkcontext::~vkcontext() { +} + +bool vkcontext::is_valid() { + return instance; +} + +void vkcontext::message(uint32_t severity, + uint32_t type, + const cstring& id, + const cstring& message, + const dynarray& queue, + const dynarray& commands, + const dynarray& objects) { + + if (id == "specialuse-extension") { + return; + } + + logger::log(translate_severity(severity), format( + "\n\t[Vulkan Message] \"{}\" - #{}\n\t{}\n\tObjects = {}\n\tQueue = {}\n\tCommands = {}", + vk::message_type_string(type), id, message, + objects, queue, commands + )); +} +} // fennec \ No newline at end of file diff --git a/include/fennec/renderers/vulkan/vkcontext.cpp b/source/renderers/vulkan/vksurface.cpp similarity index 70% rename from include/fennec/renderers/vulkan/vkcontext.cpp rename to source/renderers/vulkan/vksurface.cpp index 8fc58bc..274c19e 100644 --- a/include/fennec/renderers/vulkan/vkcontext.cpp +++ b/source/renderers/vulkan/vksurface.cpp @@ -1,6 +1,6 @@ // ===================================================================================================================== // fennec, a free and open source game engine -// Copyright © 2025 - 2026 Medusa Slockbower +// Copyright © 2025 Medusa Slockbower // // This program is free software: you can redistribute it and/or modify // it under the terms of the GNU General Public License as published by @@ -16,20 +16,30 @@ // along with this program. If not, see . // ===================================================================================================================== +#include -#include +namespace fennec +{ -namespace fennec { - -vkcontext::vkcontext(display_server* display) - : gfxcontext(display) { +vksurface::vksurface(fennec::window* win, gfxcontext* ctx, surface_t&& surface) + : gfxsurface(win, ctx) + , _surface(fennec::forward(surface)) { } -vkcontext::~vkcontext() { +vksurface::~vksurface() { + } -bool vkcontext::is_valid() { - return false; +void vksurface::make_current() { + } -} // fennec \ No newline at end of file +void vksurface::swap() { + +} + +void vksurface::resize(const ivec2&) { + +} + +} diff --git a/source/scene/scene.cpp b/source/scene/scene.cpp index 3d05fee..66586a4 100644 --- a/source/scene/scene.cpp +++ b/source/scene/scene.cpp @@ -24,16 +24,16 @@ namespace fennec scene_node* scene::operator[](const cstring& name) const { list parse; - parse.push_back(table_t::root); + parse.push_back(tree_t::root); while (not parse.is_empty()) { - size_t n = parse.front(); - if (_table[n]->name == name) { - return _table[n].get(); + const size_t n = parse.front(); + if (_tree[n]->name == name) { + return _tree[n].get(); } // Pre-Order traversal - parse.push_front(_table.next(n)); - parse.push_front(_table.child(n)); + parse.push_front(_tree.next(n)); + parse.push_front(_tree.child(n)); parse.pop_front(); } return nullptr; @@ -41,16 +41,16 @@ scene_node* scene::operator[](const cstring& name) const { scene_node* scene::operator[](const string& name) const { list parse; - parse.push_back(table_t::root); + parse.push_back(tree_t::root); while (not parse.is_empty()) { - size_t n = parse.front(); - if (_table[n]->name == name) { - return _table[n].get(); + const size_t n = parse.front(); + if (_tree[n]->name == name) { + return _tree[n].get(); } // Pre-Order traversal - parse.push_front(_table.next(n)); - parse.push_front(_table.child(n)); + parse.push_front(_tree.next(n)); + parse.push_front(_tree.child(n)); parse.pop_front(); } return nullptr; diff --git a/test/CMakeLists.txt b/test/CMakeLists.txt index 40b8ab8..5699da0 100644 --- a/test/CMakeLists.txt +++ b/test/CMakeLists.txt @@ -12,6 +12,7 @@ add_executable(fennec-test tests/test_core.h tests/core/test_event.h tests/core/test_version.h + tests/lang/test_ranges.h ) target_compile_definitions(fennec-test PUBLIC FENNEC_TEST_CWD="${CMAKE_SOURCE_DIR}/bin/${FENNEC_BUILD_NAME}" diff --git a/test/tests/containers/test_bintree.h b/test/tests/containers/test_bintree.h index ce37a34..7eb6abe 100644 --- a/test/tests/containers/test_bintree.h +++ b/test/tests/containers/test_bintree.h @@ -70,7 +70,7 @@ inline void fennec_test_containers_bintree() { fennec_test_spacer(1); - size_t i; + size_t i = 0; i = 0; test.traverse([&](size_t x, size_t) -> uint8_t { diff --git a/test/tests/containers/test_rdtree.h b/test/tests/containers/test_rdtree.h index c0d05e3..e7c7d5a 100644 --- a/test/tests/containers/test_rdtree.h +++ b/test/tests/containers/test_rdtree.h @@ -80,7 +80,7 @@ inline void fennec_test_containers_rdtree() { fennec_test_spacer(1); - size_t i; + size_t i = 0; i = 0; test.traverse([&](size_t x, size_t) -> uint8_t { diff --git a/test/tests/lang/test_bits.h b/test/tests/lang/test_bits.h index 32ab33c..8004123 100644 --- a/test/tests/lang/test_bits.h +++ b/test/tests/lang/test_bits.h @@ -30,7 +30,7 @@ namespace fennec::test inline void fennec_test_lang_bits() { int a = 0x48ef13ad; - int b = 0x23e5ab9c; + const int b = 0x23e5ab9c; fennec_test_run(fennec::bit_cast(0x3ee00000), 0.4375f); diff --git a/test/tests/lang/test_function.h b/test/tests/lang/test_function.h index 1a29a63..27bdbac 100644 --- a/test/tests/lang/test_function.h +++ b/test/tests/lang/test_function.h @@ -33,17 +33,17 @@ inline bool fennec_test_lang_function_test() { inline void fennec_test_lang_function() { function test; - fennec_test_run((bool)(test = fennec_test_lang_function_test), true); + fennec_test_run(bool(test = fennec_test_lang_function_test), true); fennec_test_run(test(), true); fennec_test_spacer(1); - fennec_test_run((bool)(test = []() { return true; }), true); + fennec_test_run(bool(test = []() { return true; }), true); fennec_test_run(test(), true); fennec_test_spacer(1); - fennec_test_run((bool)(test = nullptr), false); + fennec_test_run(bool(test = nullptr), false); } } diff --git a/test/tests/lang/test_hashing.h b/test/tests/lang/test_hashing.h index e80a6db..603646d 100644 --- a/test/tests/lang/test_hashing.h +++ b/test/tests/lang/test_hashing.h @@ -27,10 +27,10 @@ namespace fennec::test inline void fennec_test_lang_hashing() { - size_t num = 61; - float_t numf = bit_cast((uint32_t)num); - double_t numd = bit_cast(num); - size_t exp = hash()(num); + constexpr size_t num = 61; + constexpr float_t numf = bit_cast(uint32_t(num)); + constexpr double_t numd = bit_cast(num); + constexpr size_t exp = hash()(num); fennec_test_run(hash()(num), exp); fennec_test_run(hash()(num), exp); diff --git a/test/tests/lang/test_ranges.h b/test/tests/lang/test_ranges.h new file mode 100644 index 0000000..44afb8c --- /dev/null +++ b/test/tests/lang/test_ranges.h @@ -0,0 +1,55 @@ +// ===================================================================================================================== +// fennec, a free and open source game engine +// Copyright © 2025 Medusa Slockbower +// +// This program is free software: you can redistribute it and/or modify +// it under the terms of the GNU General Public License as published by +// the Free Software Foundation, either version 3 of the License, or +// (at your option) any later version. +// +// This program is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. +// +// You should have received a copy of the GNU General Public License +// along with this program. If not, see . +// ===================================================================================================================== + +/// +/// \file test_ranges.h +/// \brief +/// +/// +/// \details +/// \author Medusa Slockbower +/// +/// \copyright Copyright © 2025 - 2026 Medusa Slockbower ([GPLv3](https://www.gnu.org/licenses/gpl-3.0.en.html)) +/// +/// + + +#ifndef FENNEC_TEST_LANG_RANGES_H +#define FENNEC_TEST_LANG_RANGES_H + +#include "../../test.h" + +#include +#include + +namespace fennec::test +{ + +inline void fennec_test_lang_ranges() { + + string res = string(10); + for (const int i : range(0, 10)) { + res[i] = char('0' + char(i)); + } + + fennec_test_run(res, string("0123456789")); +} + +} + +#endif // FENNEC_TEST_LANG_RANGES_H \ No newline at end of file diff --git a/test/tests/math/test_common.h b/test/tests/math/test_common.h index e7d2515..bf79e9b 100644 --- a/test/tests/math/test_common.h +++ b/test/tests/math/test_common.h @@ -151,9 +151,9 @@ namespace fennec::test fennec_test_spacer(1); - fennec_test_run([]() -> float { int i; float f = fennec::frexp(2.4f, i); return fennec::ldexp(f, i); }(), 2.4f); - fennec_test_run([]() -> float { int i; float f = fennec::frexp(2.5f, i); return fennec::ldexp(f, i); }(), 2.5f); - fennec_test_run([]() -> float { int i; float f = fennec::frexp(2.6f, i); return fennec::ldexp(f, i); }(), 2.6f); + fennec_test_run([]() -> float { int i; const float f = fennec::frexp(2.4f, i); return fennec::ldexp(f, i); }(), 2.4f); + fennec_test_run([]() -> float { int i; const float f = fennec::frexp(2.5f, i); return fennec::ldexp(f, i); }(), 2.5f); + fennec_test_run([]() -> float { int i; const float f = fennec::frexp(2.6f, i); return fennec::ldexp(f, i); }(), 2.6f); fennec_test_spacer(2); diff --git a/test/tests/test_lang.h b/test/tests/test_lang.h index bacf40a..01e8e0f 100644 --- a/test/tests/test_lang.h +++ b/test/tests/test_lang.h @@ -24,6 +24,7 @@ #include "lang/test_function.h" #include "lang/test_hashing.h" #include "lang/test_metaprogramming.h" +#include "lang/test_ranges.h" namespace fennec::test { @@ -47,6 +48,11 @@ namespace fennec::test fennec_test_subheader("function tests"); fennec_test_spacer(2); fennec_test_lang_function(); + fennec_test_spacer(3); + + fennec_test_subheader("ranges tests"); + fennec_test_spacer(2); + fennec_test_lang_ranges(); // TODO } diff --git a/test/tests/test_platform.h b/test/tests/test_platform.h index e04283a..1364211 100644 --- a/test/tests/test_platform.h +++ b/test/tests/test_platform.h @@ -34,7 +34,7 @@ inline void fennec_test_platform() { window_manager& wm = platform->get_window_manager(); - window_id window = wm.create_window(window::config { + const window_id window = wm.create_window(window::config { .title = string("fennec-test"), .flags = { }, .mode = window::mode_windowed, diff --git a/test/tests/test_threading.h b/test/tests/test_threading.h index 3d4fc45..77a74ff 100644 --- a/test/tests/test_threading.h +++ b/test/tests/test_threading.h @@ -105,7 +105,7 @@ inline void fennec_test_threading_run_test_mpscq(array& thread template inline double fennec_test_threading_timed(ReturnT (func)(ParamsT...), ArgsT&&...args) { - auto start = std::chrono::high_resolution_clock::now(); + const auto start = std::chrono::high_resolution_clock::now(); func(fennec::forward(args)...); return std::chrono::duration(std::chrono::high_resolution_clock::now() - start).count(); }