mirror of https://github.com/mosra/magnum.git
10 changed files with 547 additions and 3 deletions
@ -0,0 +1,123 @@ |
|||||||
|
/*
|
||||||
|
This file is part of Magnum. |
||||||
|
|
||||||
|
Copyright © 2010, 2011, 2012, 2013, 2014, 2015, 2016, 2017, 2018, 2019, |
||||||
|
2020 Vladimír Vondruš <mosra@centrum.cz> |
||||||
|
|
||||||
|
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. |
||||||
|
*/ |
||||||
|
|
||||||
|
#include "DeviceProperties.h" |
||||||
|
|
||||||
|
#include <Corrade/Containers/Array.h> |
||||||
|
#include <Corrade/Containers/StringView.h> |
||||||
|
#include <Corrade/Utility/Debug.h> |
||||||
|
|
||||||
|
#include "Magnum/Vk/Instance.h" |
||||||
|
#include "Magnum/Vk/Result.h" |
||||||
|
#include "Magnum/Vk/Implementation/InstanceState.h" |
||||||
|
|
||||||
|
namespace Magnum { namespace Vk { |
||||||
|
|
||||||
|
struct DeviceProperties::State { |
||||||
|
VkPhysicalDeviceProperties2 properties{}; |
||||||
|
}; |
||||||
|
|
||||||
|
DeviceProperties::DeviceProperties(NoCreateT) noexcept: _instance{}, _handle{} {} |
||||||
|
|
||||||
|
DeviceProperties::DeviceProperties(Instance& instance, VkPhysicalDevice handle): _instance{&instance}, _handle{handle} {} |
||||||
|
|
||||||
|
/* The VkDeviceProperties handle doesn't need to be destroyed so it's enough to
|
||||||
|
just rely on the implicit behavior */ |
||||||
|
DeviceProperties::DeviceProperties(DeviceProperties&&) noexcept = default; |
||||||
|
|
||||||
|
DeviceProperties::~DeviceProperties() = default; |
||||||
|
|
||||||
|
DeviceProperties& DeviceProperties::operator=(DeviceProperties&&) noexcept = default; |
||||||
|
|
||||||
|
Containers::StringView DeviceProperties::name() { |
||||||
|
return properties().properties.deviceName; |
||||||
|
} |
||||||
|
|
||||||
|
const VkPhysicalDeviceProperties2& DeviceProperties::properties() { |
||||||
|
if(!_state) _state.emplace(); |
||||||
|
|
||||||
|
/* Properties not fetched yet, do that now */ |
||||||
|
if(!_state->properties.sType) { |
||||||
|
_state->properties.sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_PROPERTIES_2; |
||||||
|
|
||||||
|
_instance->state().getPhysicalDevicePropertiesImplementation(*this, _state->properties); |
||||||
|
} |
||||||
|
|
||||||
|
return _state->properties; |
||||||
|
} |
||||||
|
|
||||||
|
void DeviceProperties::getPropertiesImplementationDefault(DeviceProperties& self, VkPhysicalDeviceProperties2& properties) { |
||||||
|
return (**self._instance).GetPhysicalDeviceProperties(self._handle, &properties.properties); |
||||||
|
} |
||||||
|
|
||||||
|
void DeviceProperties::getPropertiesImplementationKHR(DeviceProperties& self, VkPhysicalDeviceProperties2& properties) { |
||||||
|
return (**self._instance).GetPhysicalDeviceProperties2KHR(self._handle, &properties); |
||||||
|
} |
||||||
|
|
||||||
|
void DeviceProperties::getPropertiesImplementation11(DeviceProperties& self, VkPhysicalDeviceProperties2& properties) { |
||||||
|
return (**self._instance).GetPhysicalDeviceProperties2(self._handle, &properties); |
||||||
|
} |
||||||
|
|
||||||
|
Containers::Array<DeviceProperties> enumerateDevices(Instance& instance) { |
||||||
|
/* Retrieve total device count */ |
||||||
|
UnsignedInt count; |
||||||
|
MAGNUM_VK_INTERNAL_ASSERT_RESULT(instance->EnumeratePhysicalDevices(instance, &count, nullptr)); |
||||||
|
|
||||||
|
/* Allocate memory for the output, fetch the handles into it */ |
||||||
|
Containers::Array<DeviceProperties> out{Containers::NoInit, count}; |
||||||
|
Containers::ArrayView<VkPhysicalDevice> handles{reinterpret_cast<VkPhysicalDevice*>(out.data()), count}; |
||||||
|
MAGNUM_VK_INTERNAL_ASSERT_RESULT(instance->EnumeratePhysicalDevices(instance, &count, handles.data())); |
||||||
|
|
||||||
|
/* Expect the device count didn't change between calls */ |
||||||
|
CORRADE_INTERNAL_ASSERT(count == out.size()); |
||||||
|
|
||||||
|
/* Construct actual DeviceProperties instances from these, go backwards so
|
||||||
|
we don't overwrite the not-yet-processed handles */ |
||||||
|
for(std::size_t i = count; i != 0; --i) |
||||||
|
new(out.data() + i - 1) DeviceProperties{instance, handles[i - 1]}; |
||||||
|
|
||||||
|
return out; |
||||||
|
} |
||||||
|
|
||||||
|
Debug& operator<<(Debug& debug, const DeviceType value) { |
||||||
|
debug << "Vk::DeviceType" << Debug::nospace; |
||||||
|
|
||||||
|
switch(value) { |
||||||
|
/* LCOV_EXCL_START */ |
||||||
|
#define _c(value) case Vk::DeviceType::value: return debug << "::" << Debug::nospace << #value; |
||||||
|
_c(Other) |
||||||
|
_c(IntegratedGpu) |
||||||
|
_c(DiscreteGpu) |
||||||
|
_c(VirtualGpu) |
||||||
|
_c(Cpu) |
||||||
|
#undef _c |
||||||
|
/* LCOV_EXCL_STOP */ |
||||||
|
} |
||||||
|
|
||||||
|
/* Vulkan docs have the values in decimal, so not converting to hex */ |
||||||
|
return debug << "(" << Debug::nospace << Int(value) << Debug::nospace << ")"; |
||||||
|
} |
||||||
|
|
||||||
|
}} |
||||||
@ -0,0 +1,218 @@ |
|||||||
|
#ifndef Magnum_Vk_DeviceProperties_h |
||||||
|
#define Magnum_Vk_DeviceProperties_h |
||||||
|
/*
|
||||||
|
This file is part of Magnum. |
||||||
|
|
||||||
|
Copyright © 2010, 2011, 2012, 2013, 2014, 2015, 2016, 2017, 2018, 2019, |
||||||
|
2020 Vladimír Vondruš <mosra@centrum.cz> |
||||||
|
|
||||||
|
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. |
||||||
|
*/ |
||||||
|
|
||||||
|
/** @file
|
||||||
|
* @brief Class @ref Magnum::Vk::DeviceProperties, enum @ref Magnum::Vk::DeviceType, function @ref Magnum::Vk::enumerateDevices() |
||||||
|
* @m_since_latest |
||||||
|
*/ |
||||||
|
|
||||||
|
#include <Corrade/Containers/Pointer.h> |
||||||
|
#include <Corrade/Containers/Reference.h> |
||||||
|
|
||||||
|
#include "Magnum/Magnum.h" |
||||||
|
#include "Magnum/Tags.h" |
||||||
|
#include "Magnum/Vk/Vulkan.h" |
||||||
|
#include "Magnum/Vk/Vk.h" |
||||||
|
#include "Magnum/Vk/visibility.h" |
||||||
|
|
||||||
|
namespace Magnum { namespace Vk { |
||||||
|
|
||||||
|
namespace Implementation { struct InstanceState; } |
||||||
|
|
||||||
|
/**
|
||||||
|
@brief Physical device type |
||||||
|
@m_since_latest |
||||||
|
|
||||||
|
Wraps a @type_vk_keyword{PhysicalDeviceType}. |
||||||
|
@see @ref DeviceProperties::type() |
||||||
|
@m_enum_values_as_keywords |
||||||
|
*/ |
||||||
|
enum class DeviceType: Int { |
||||||
|
/** Anything that does not match any other available types */ |
||||||
|
Other = VK_PHYSICAL_DEVICE_TYPE_OTHER, |
||||||
|
|
||||||
|
/**
|
||||||
|
* Typically a device embedded in or tightly coupled with the host |
||||||
|
*/ |
||||||
|
IntegratedGpu = VK_PHYSICAL_DEVICE_TYPE_INTEGRATED_GPU, |
||||||
|
|
||||||
|
/**
|
||||||
|
* Typically a separate processor connected to the host via an |
||||||
|
* interlink |
||||||
|
*/ |
||||||
|
DiscreteGpu = VK_PHYSICAL_DEVICE_TYPE_DISCRETE_GPU, |
||||||
|
|
||||||
|
/** Typically a virtual node in a virtualization environment */ |
||||||
|
VirtualGpu = VK_PHYSICAL_DEVICE_TYPE_VIRTUAL_GPU, |
||||||
|
|
||||||
|
/** Typically running on the same processors as the host */ |
||||||
|
Cpu = VK_PHYSICAL_DEVICE_TYPE_CPU |
||||||
|
}; |
||||||
|
|
||||||
|
/**
|
||||||
|
@debugoperatorclassenum{DeviceProperties,DeviceType} |
||||||
|
@m_since_latest |
||||||
|
*/ |
||||||
|
MAGNUM_VK_EXPORT Debug& operator<<(Debug& debug, DeviceType value); |
||||||
|
|
||||||
|
/**
|
||||||
|
@brief Physical device properties |
||||||
|
@m_since_latest |
||||||
|
|
||||||
|
Wraps a @type_vk_keyword{PhysicalDevice} along with its (lazy-populated) |
||||||
|
properties. |
||||||
|
@see @ref enumeratePhysicalDevices() |
||||||
|
*/ |
||||||
|
class MAGNUM_VK_EXPORT DeviceProperties { |
||||||
|
public: |
||||||
|
/**
|
||||||
|
* @brief Wrap existing Vulkan physical device |
||||||
|
* @param instance Vulkan instance |
||||||
|
* @param handle The @type_vk{PhysicalDevice} handle |
||||||
|
* |
||||||
|
* The @p handle is expected to be originating from @p instance. Unlike |
||||||
|
* with other handle types, the @type_vk{PhysicalDevice} handles don't |
||||||
|
* have to be destroyed at the end. so there's no equivalent of e.g. |
||||||
|
* @ref Instance::release() or @ref Instance::handleFlags(). |
||||||
|
*/ |
||||||
|
static DeviceProperties wrap(Instance& instance, VkPhysicalDevice handle) { |
||||||
|
return DeviceProperties{instance, handle}; |
||||||
|
} |
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief Construct without populating the contents |
||||||
|
* |
||||||
|
* The constructed instance is equivalent to moved-from state. Useful |
||||||
|
* in cases where you will overwrite the instance later anyway. Move |
||||||
|
* another object over it to make it useful. |
||||||
|
*/ |
||||||
|
explicit DeviceProperties(NoCreateT) noexcept; |
||||||
|
|
||||||
|
/** @brief Copying is not allowed */ |
||||||
|
DeviceProperties(const DeviceProperties&) = delete; |
||||||
|
|
||||||
|
/** @brief Move constructor */ |
||||||
|
DeviceProperties(DeviceProperties&&) noexcept; |
||||||
|
|
||||||
|
~DeviceProperties(); |
||||||
|
|
||||||
|
/** @brief Copying is not allowed */ |
||||||
|
DeviceProperties& operator=(const DeviceProperties&) = delete; |
||||||
|
|
||||||
|
/** @brief Move assignment */ |
||||||
|
DeviceProperties& operator=(DeviceProperties&&) noexcept; |
||||||
|
|
||||||
|
/** @brief Underlying @type_vk{PhysicalDevice} handle */ |
||||||
|
VkPhysicalDevice handle() { return _handle; } |
||||||
|
/** @overload */ |
||||||
|
operator VkPhysicalDevice() { return _handle; } |
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief Raw device properties |
||||||
|
* |
||||||
|
* Populated lazily on first request. If Vulkan 1.1 or the |
||||||
|
* @vk_extension{KHR,get_physical_device_properties2} extension is not |
||||||
|
* enabled on the originating instance, only the Vulkan 1.0 subset of |
||||||
|
* device properties is queried, with the `pNext` member being |
||||||
|
* @cpp nullptr @ce. |
||||||
|
* @see @fn_vk_keyword{GetPhysicalDeviceProperties2}, |
||||||
|
* @fn_vk_keyword{GetPhysicalDeviceProperties} |
||||||
|
*/ |
||||||
|
const VkPhysicalDeviceProperties2& properties(); |
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief API version |
||||||
|
* |
||||||
|
* Convenience access to @ref properties() internals, populated lazily |
||||||
|
* on first request. |
||||||
|
*/ |
||||||
|
Version apiVersion() { |
||||||
|
return Version(properties().properties.apiVersion); |
||||||
|
} |
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief Driver version |
||||||
|
* |
||||||
|
* Convenience access to @ref properties() internals, populated lazily |
||||||
|
* on first request. |
||||||
|
*/ |
||||||
|
Version driverVersion() { |
||||||
|
return Version(properties().properties.driverVersion); |
||||||
|
} |
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief Device type |
||||||
|
* |
||||||
|
* Convenience access to @ref properties() internals, populated lazily |
||||||
|
* on first request. |
||||||
|
*/ |
||||||
|
DeviceType type() { |
||||||
|
return DeviceType(properties().properties.deviceType); |
||||||
|
} |
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief Device name |
||||||
|
* |
||||||
|
* Convenience access to @ref properties() internals, populated lazily |
||||||
|
* on first request. |
||||||
|
*/ |
||||||
|
Containers::StringView name(); |
||||||
|
|
||||||
|
private: |
||||||
|
friend Implementation::InstanceState; |
||||||
|
|
||||||
|
#ifndef DOXYGEN_GENERATING_OUTPUT |
||||||
|
/* The DAMN THING lists this among friends, which is AN IMPLEMENTATION
|
||||||
|
DETAIL */ |
||||||
|
friend MAGNUM_VK_EXPORT Containers::Array<DeviceProperties> enumerateDevices(Instance&); |
||||||
|
#endif |
||||||
|
|
||||||
|
explicit DeviceProperties(Instance& instance, VkPhysicalDevice handle); |
||||||
|
|
||||||
|
MAGNUM_VK_LOCAL static void getPropertiesImplementationDefault(DeviceProperties& self, VkPhysicalDeviceProperties2& properties); |
||||||
|
MAGNUM_VK_LOCAL static void getPropertiesImplementationKHR(DeviceProperties& self, VkPhysicalDeviceProperties2& properties); |
||||||
|
MAGNUM_VK_LOCAL static void getPropertiesImplementation11(DeviceProperties& self, VkPhysicalDeviceProperties2& properties); |
||||||
|
|
||||||
|
/* Can't be a reference because of the NoCreate constructor */ |
||||||
|
Instance* _instance; |
||||||
|
|
||||||
|
VkPhysicalDevice _handle; |
||||||
|
struct State; |
||||||
|
Containers::Pointer<State> _state; |
||||||
|
}; |
||||||
|
|
||||||
|
/**
|
||||||
|
@brief Enumerate physical devices |
||||||
|
@m_since_latest |
||||||
|
|
||||||
|
@see @fn_vk_keyword{EnumeratePhysicalDevices} |
||||||
|
*/ |
||||||
|
MAGNUM_VK_EXPORT Containers::Array<DeviceProperties> enumerateDevices(Instance& instance); |
||||||
|
|
||||||
|
}} |
||||||
|
|
||||||
|
#endif |
||||||
@ -0,0 +1,73 @@ |
|||||||
|
/*
|
||||||
|
This file is part of Magnum. |
||||||
|
|
||||||
|
Copyright © 2010, 2011, 2012, 2013, 2014, 2015, 2016, 2017, 2018, 2019, |
||||||
|
2020 Vladimír Vondruš <mosra@centrum.cz> |
||||||
|
|
||||||
|
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. |
||||||
|
*/ |
||||||
|
|
||||||
|
#include <sstream> |
||||||
|
#include <Corrade/TestSuite/Tester.h> |
||||||
|
#include <Corrade/Utility/DebugStl.h> |
||||||
|
|
||||||
|
#include "Magnum/Vk/DeviceProperties.h" |
||||||
|
|
||||||
|
namespace Magnum { namespace Vk { namespace Test { namespace { |
||||||
|
|
||||||
|
struct DevicePropertiesTest: TestSuite::Tester { |
||||||
|
explicit DevicePropertiesTest(); |
||||||
|
|
||||||
|
void constructNoCreate(); |
||||||
|
void constructCopy(); |
||||||
|
|
||||||
|
void debugDeviceType(); |
||||||
|
}; |
||||||
|
|
||||||
|
DevicePropertiesTest::DevicePropertiesTest() { |
||||||
|
addTests({&DevicePropertiesTest::constructNoCreate, |
||||||
|
&DevicePropertiesTest::constructCopy, |
||||||
|
|
||||||
|
&DevicePropertiesTest::debugDeviceType}); |
||||||
|
} |
||||||
|
|
||||||
|
void DevicePropertiesTest::constructNoCreate() { |
||||||
|
{ |
||||||
|
DeviceProperties properties{NoCreate}; |
||||||
|
CORRADE_VERIFY(!properties.handle()); |
||||||
|
} |
||||||
|
|
||||||
|
/* Implicit construction is not allowed */ |
||||||
|
CORRADE_VERIFY(!(std::is_convertible<NoCreateT, DeviceProperties>::value)); |
||||||
|
} |
||||||
|
|
||||||
|
void DevicePropertiesTest::constructCopy() { |
||||||
|
CORRADE_VERIFY(!(std::is_constructible<DeviceProperties, const DeviceProperties&>{})); |
||||||
|
CORRADE_VERIFY(!(std::is_assignable<DeviceProperties, const DeviceProperties&>{})); |
||||||
|
} |
||||||
|
|
||||||
|
void DevicePropertiesTest::debugDeviceType() { |
||||||
|
std::ostringstream out; |
||||||
|
Debug{&out} << DeviceType::DiscreteGpu << DeviceType(-10007655); |
||||||
|
CORRADE_COMPARE(out.str(), "Vk::DeviceType::DiscreteGpu Vk::DeviceType(-10007655)\n"); |
||||||
|
} |
||||||
|
|
||||||
|
}}}} |
||||||
|
|
||||||
|
CORRADE_TEST_MAIN(Magnum::Vk::Test::DevicePropertiesTest) |
||||||
@ -0,0 +1,110 @@ |
|||||||
|
/*
|
||||||
|
This file is part of Magnum. |
||||||
|
|
||||||
|
Copyright © 2010, 2011, 2012, 2013, 2014, 2015, 2016, 2017, 2018, 2019, |
||||||
|
2020 Vladimír Vondruš <mosra@centrum.cz> |
||||||
|
|
||||||
|
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. |
||||||
|
*/ |
||||||
|
|
||||||
|
#include <Corrade/Containers/Array.h> |
||||||
|
#include <Corrade/Containers/StringView.h> |
||||||
|
#include <Corrade/TestSuite/Tester.h> |
||||||
|
#include <Corrade/TestSuite/Compare/Numeric.h> |
||||||
|
|
||||||
|
#include "Magnum/Vk/DeviceProperties.h" |
||||||
|
#include "Magnum/Vk/Instance.h" |
||||||
|
#include "Magnum/Vk/Result.h" |
||||||
|
#include "Magnum/Vk/Version.h" |
||||||
|
|
||||||
|
namespace Magnum { namespace Vk { namespace Test { namespace { |
||||||
|
|
||||||
|
struct DevicePropertiesVkTest: TestSuite::Tester { |
||||||
|
explicit DevicePropertiesVkTest(); |
||||||
|
|
||||||
|
void enumerate(); |
||||||
|
void constructMove(); |
||||||
|
void wrap(); |
||||||
|
|
||||||
|
Instance _instance; |
||||||
|
}; |
||||||
|
|
||||||
|
DevicePropertiesVkTest::DevicePropertiesVkTest(): _instance{InstanceCreateInfo{arguments().first, arguments().second}} { |
||||||
|
addTests({&DevicePropertiesVkTest::enumerate, |
||||||
|
&DevicePropertiesVkTest::constructMove, |
||||||
|
&DevicePropertiesVkTest::wrap}); |
||||||
|
} |
||||||
|
|
||||||
|
void DevicePropertiesVkTest::enumerate() { |
||||||
|
Containers::Array<DeviceProperties> devices = enumerateDevices(_instance); |
||||||
|
Debug{} << "Found" << devices.size() << "devices"; |
||||||
|
CORRADE_VERIFY(!devices.empty()); |
||||||
|
|
||||||
|
for(DeviceProperties& device: devices) { |
||||||
|
CORRADE_ITERATION(device.name()); |
||||||
|
|
||||||
|
CORRADE_VERIFY(device.handle()); |
||||||
|
CORRADE_COMPARE_AS(device.apiVersion(), Version::Vk10, |
||||||
|
TestSuite::Compare::GreaterOrEqual); |
||||||
|
CORRADE_COMPARE_AS(device.driverVersion(), Version::Vk10, |
||||||
|
TestSuite::Compare::GreaterOrEqual); |
||||||
|
CORRADE_VERIFY(device.type() != DeviceType::Other); |
||||||
|
CORRADE_VERIFY(!device.name().isEmpty()); |
||||||
|
} |
||||||
|
} |
||||||
|
|
||||||
|
void DevicePropertiesVkTest::constructMove() { |
||||||
|
Containers::Array<DeviceProperties> devices = enumerateDevices(_instance); |
||||||
|
CORRADE_VERIFY(!devices.empty()); |
||||||
|
VkPhysicalDevice handle = devices[0].handle(); |
||||||
|
Containers::StringView name = devices[0].name(); |
||||||
|
|
||||||
|
DeviceProperties a = std::move(devices[0]); |
||||||
|
CORRADE_COMPARE(a.handle(), handle); |
||||||
|
CORRADE_COMPARE(a.name(), name); |
||||||
|
|
||||||
|
DeviceProperties b = DeviceProperties::wrap(_instance, nullptr); |
||||||
|
b = std::move(a); |
||||||
|
CORRADE_COMPARE(b.handle(), handle); |
||||||
|
CORRADE_COMPARE(b.name(), name); |
||||||
|
|
||||||
|
CORRADE_VERIFY(std::is_nothrow_move_constructible<DeviceProperties>::value); |
||||||
|
CORRADE_VERIFY(std::is_nothrow_move_assignable<DeviceProperties>::value); |
||||||
|
} |
||||||
|
|
||||||
|
void DevicePropertiesVkTest::wrap() { |
||||||
|
VkPhysicalDevice handle; |
||||||
|
UnsignedInt count = 1; |
||||||
|
auto result = Result(_instance->EnumeratePhysicalDevices(_instance, &count, &handle)); |
||||||
|
{ |
||||||
|
/** @todo clean up once Compare::AnyOf exists */ |
||||||
|
CORRADE_ITERATION(result); |
||||||
|
CORRADE_VERIFY(result == Result::Success || result == Result::Incomplete); |
||||||
|
} |
||||||
|
|
||||||
|
DeviceProperties wrapped = DeviceProperties::wrap(_instance, handle); |
||||||
|
CORRADE_VERIFY(wrapped.handle()); |
||||||
|
|
||||||
|
Containers::Array<DeviceProperties> devices = enumerateDevices(_instance); |
||||||
|
CORRADE_COMPARE(wrapped.name(), devices[0].name()); |
||||||
|
} |
||||||
|
|
||||||
|
}}}} |
||||||
|
|
||||||
|
CORRADE_TEST_MAIN(Magnum::Vk::Test::DevicePropertiesVkTest) |
||||||
Loading…
Reference in new issue