Revert "Collapsed ExtensionFeatures and StructureContainer together into FeaturesContainer. After the purging of the function pointers all ExtensionFeatures was doing was just wrapping StructureContainers functions."

This reverts commit 2f69fa52cb.
This commit is contained in:
Charles Giessen 2021-04-18 14:09:12 -06:00
parent 2a352b5a25
commit 64aeed5855
2 changed files with 90 additions and 58 deletions

View File

@ -846,8 +846,8 @@ std::vector<const char*> check_device_extension_support(
// clang-format off
bool supports_features(VkPhysicalDeviceFeatures supported,
VkPhysicalDeviceFeatures requested,
std::vector<FeaturesContainer> const& extension_supported,
std::vector<FeaturesContainer> const& extension_requested) {
std::vector<ExtensionFeatures> const& extension_supported,
std::vector<ExtensionFeatures> const& extension_requested) {
if (requested.robustBufferAccess && !supported.robustBufferAccess) return false;
if (requested.fullDrawIndexUint32 && !supported.fullDrawIndexUint32) return false;
if (requested.imageCubeArray && !supported.imageCubeArray) return false;
@ -992,7 +992,7 @@ uint32_t get_present_queue_index(VkPhysicalDevice const phys_device,
PhysicalDeviceSelector::PhysicalDeviceDesc PhysicalDeviceSelector::populate_device_details(
uint32_t instance_version, VkPhysicalDevice phys_device,
std::vector<detail::FeaturesContainer> extension_features_as_template) const {
std::vector<detail::ExtensionFeatures> extension_features_as_template) const {
PhysicalDeviceSelector::PhysicalDeviceDesc desc{};
desc.phys_device = phys_device;
auto queue_families = detail::get_vector_noerror<VkQueueFamilyProperties>(
@ -1007,15 +1007,15 @@ PhysicalDeviceSelector::PhysicalDeviceDesc PhysicalDeviceSelector::populate_devi
desc.device_features2.sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_FEATURES_2;
desc.extension_features = extension_features_as_template;
if (instance_version >= VK_API_VERSION_1_1) {
detail::FeaturesContainer* prev = nullptr;
detail::ExtensionFeatures* prev = nullptr;
for(auto& extension : desc.extension_features) {
if(prev != nullptr) {
prev->header->pNext = extension.header;
prev->structure.header->pNext = extension.structure.header;
}
prev = &extension;
}
if(desc.extension_features.size() > 0) {
desc.device_features2.pNext = desc.extension_features.front().header;
desc.device_features2.pNext = desc.extension_features.front().structure.header;
}
detail::vulkan_functions().fp_vkGetPhysicalDeviceFeatures2(phys_device, &desc.device_features2);
}
@ -1402,20 +1402,22 @@ detail::Result<Device> DeviceBuilder::build() const {
#if defined(VK_API_VERSION_1_1)
// Setup the pNexts of all the extension features
std::vector<detail::FeaturesContainer> match = physical_device.extension_features;
std::vector<detail::ExtensionFeatures> match = physical_device.extension_features;
VkPhysicalDeviceFeatures2 local_features2{};
//VkBaseOutStructure* tail = nullptr;
if (physical_device.instance_version >= VK_MAKE_VERSION(1, 1, 0) &&
match.size() > 0) {
detail::FeaturesContainer* prev = nullptr;
detail::ExtensionFeatures* prev = nullptr;
for(auto& extension : match) {
if(prev != nullptr) {
prev->header->pNext = extension.header;
prev->structure.header->pNext = extension.structure.header;
}
prev = &extension;
//tail = prev->structure;
}
local_features2.sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_FEATURES_2;
local_features2.features = physical_device.features;
local_features2.pNext = match.front().header;
local_features2.pNext = match.front().structure.header;
has_phys_dev_features_2 = true;
}
#endif
@ -1435,7 +1437,7 @@ detail::Result<Device> DeviceBuilder::build() const {
if (has_phys_dev_features_2) {
device_create_info.pNext = &local_features2;
if(info.pNext_chain.size() > 0) {
match.back().header->pNext = info.pNext_chain.front();
match.back().structure.header->pNext = info.pNext_chain.front();
}
} else {
device_create_info.pEnabledFeatures = &physical_device.features;

View File

@ -115,36 +115,35 @@ template <typename T> class Result {
bool m_init;
};
struct FeaturesContainer {
struct ExtensionFeatures {
FeaturesContainer() = default;
struct StructureContainer {
FeaturesContainer(FeaturesContainer const& other) { copy(other); }
struct Header {
VkStructureType sType;
void* pNext;
};
FeaturesContainer(FeaturesContainer&& other) { copy(other); }
StructureContainer() = default;
FeaturesContainer& operator=(FeaturesContainer const& other) { copy(other); return *this; }
StructureContainer (StructureContainer const& other) { copy(other); }
FeaturesContainer& operator=(FeaturesContainer&& other) { copy(other); return *this; }
StructureContainer (StructureContainer&& other) { copy(other); }
template <typename T>
static FeaturesContainer make(T src) {
FeaturesContainer extension_features;
extension_features.set<T>(src);
return extension_features;
StructureContainer& operator=(StructureContainer const& other) { copy(other); return *this; }
}
StructureContainer& operator=(StructureContainer&& other) { copy(other); return *this; }
template <typename T>
void set(T const& features) {
data.resize(sizeof(T));
*reinterpret_cast<T*>(data.data()) = features;
count = (sizeof(T) - sizeof(VkBaseOutStructure)) / sizeof(VkBool32);
header = reinterpret_cast<VkBaseOutStructure*>(data.data());
fields = reinterpret_cast<VkBool32*>(data.data() + sizeof(VkBaseOutStructure));
count = (sizeof(T) - sizeof(Header)) / sizeof(VkBool32);
header = reinterpret_cast<Header*>(data.data());
fields = reinterpret_cast<VkBool32*>(data.data() + sizeof(Header));
}
bool match(FeaturesContainer const& other) const {
bool match(StructureContainer const& other) const {
if(!header || !other.header || header->sType != other.header->sType) { return false; }
for(auto i = 0; i < count; ++i) {
if(fields[i] == VK_TRUE && other.fields[i] == VK_FALSE) {
@ -154,15 +153,15 @@ struct FeaturesContainer {
return true;
}
VkBaseOutStructure* header = nullptr;
Header* header = nullptr;
private:
// Just to avoid having it copied in 4 places
void copy(FeaturesContainer const& other) {
void copy(StructureContainer const& other) {
data = other.data;
count = other.count;
header = reinterpret_cast<VkBaseOutStructure*>(data.data());
fields = reinterpret_cast<VkBool32*>(data.data() + sizeof(VkBaseOutStructure));
header = reinterpret_cast<Header*>(data.data());
fields = reinterpret_cast<VkBool32*>(data.data() + sizeof(Header));
}
std::vector<char> data;
@ -172,6 +171,37 @@ private:
};
ExtensionFeatures() = default;
ExtensionFeatures (ExtensionFeatures const& other) : structure(other.structure) {}
ExtensionFeatures (ExtensionFeatures&& other) : structure(std::exchange(other.structure, {})) {}
ExtensionFeatures& operator=(ExtensionFeatures const& other) {
structure = other.structure;
return *this;
}
ExtensionFeatures& operator=(ExtensionFeatures&& other) {
structure = std::exchange(other.structure, {});
return *this;
}
template <typename T>
static ExtensionFeatures make(T src) {
ExtensionFeatures extension_features;
extension_features.structure.set<T>(src);
return extension_features;
}
bool match(const ExtensionFeatures& other) const { return structure.match(other.structure); }
StructureContainer structure;
};
} // namespace detail
enum class InstanceError {
@ -412,7 +442,7 @@ struct PhysicalDevice {
uint32_t instance_version = VK_MAKE_VERSION(1, 0, 0);
std::vector<const char*> extensions_to_enable;
std::vector<VkQueueFamilyProperties> queue_families;
std::vector<detail::FeaturesContainer> extension_features;
std::vector<detail::ExtensionFeatures> extension_features;
bool defer_surface_initialization = false;
friend class PhysicalDeviceSelector;
friend class DeviceBuilder;
@ -479,7 +509,7 @@ class PhysicalDeviceSelector {
PhysicalDeviceSelector& add_required_extension_features(T const& features) {
assert(features.sType != 0 &&
"Features struct sType must be filled with the struct's corresponding VkStructureType enum");
criteria.extension_features.push_back(detail::FeaturesContainer::make(features));
criteria.extension_features.push_back(detail::ExtensionFeatures::make(features));
return *this;
}
#endif
@ -521,7 +551,7 @@ class PhysicalDeviceSelector {
VkPhysicalDeviceMemoryProperties mem_properties{};
#if defined(VK_API_VERSION_1_1)
VkPhysicalDeviceFeatures2 device_features2{};
std::vector<detail::FeaturesContainer> extension_features;
std::vector<detail::ExtensionFeatures> extension_features;
#endif
};
@ -530,7 +560,7 @@ class PhysicalDeviceSelector {
PhysicalDeviceDesc populate_device_details(uint32_t instance_version,
VkPhysicalDevice phys_device,
std::vector<detail::FeaturesContainer> extension_features_as_template) const;
std::vector<detail::ExtensionFeatures> extension_features_as_template) const;
struct SelectionCriteria {
PreferredDeviceType preferred_type = PreferredDeviceType::discrete;
@ -552,7 +582,7 @@ class PhysicalDeviceSelector {
VkPhysicalDeviceFeatures required_features{};
#if defined(VK_API_VERSION_1_1)
VkPhysicalDeviceFeatures2 required_features2{};
std::vector<detail::FeaturesContainer> extension_features;
std::vector<detail::ExtensionFeatures> extension_features;
#endif
bool defer_surface_initialization = false;
bool use_first_gpu_unconditionally = false;