blob: e06d88ec75ff54b95866f486393d82ee5d4a3436 [file] [log] [blame]
/*
* Copyright (c) 2021-2023 The Khronos Group Inc.
* Copyright (c) 2021-2023 Valve Corporation
* Copyright (c) 2021-2023 LunarG, Inc.
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and/or associated documentation files (the "Materials"), to
* deal in the Materials without restriction, including without limitation the
* rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
* sell copies of the Materials, and to permit persons to whom the Materials are
* furnished to do so, subject to the following conditions:
*
* The above copyright notice(s) and this permission notice shall be included in
* all copies or substantial portions of the Materials.
*
* THE MATERIALS ARE 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 MATERIALS OR THE
* USE OR OTHER DEALINGS IN THE MATERIALS.
*
* Author: Charles Giessen <charles@lunarg.com>
*/
#include "test_environment.h"
void CheckLogForLayerString(FrameworkEnvironment& env, const char* implicit_layer_name, bool check_for_enable) {
{
InstWrapper inst{env.vulkan_functions};
FillDebugUtilsCreateDetails(inst.create_info, env.debug_log);
inst.CheckCreate(VK_SUCCESS);
if (check_for_enable) {
ASSERT_TRUE(env.debug_log.find(std::string("Insert instance layer \"") + implicit_layer_name));
} else {
ASSERT_FALSE(env.debug_log.find(std::string("Insert instance layer \"") + implicit_layer_name));
}
}
env.debug_log.clear();
}
const char* lunarg_meta_layer_name = "VK_LAYER_LUNARG_override";
TEST(ImplicitLayers, WithEnableAndDisableEnvVar) {
FrameworkEnvironment env;
env.add_icd(TestICDDetails(TEST_ICD_PATH_VERSION_2_EXPORT_ICD_GPDPA));
const char* implicit_layer_name = "VK_LAYER_ImplicitTestLayer";
EnvVarWrapper enable_env_var{"ENABLE_ME"};
EnvVarWrapper disable_env_var{"DISABLE_ME"};
env.add_implicit_layer(ManifestLayer{}.add_layer(ManifestLayer::LayerDescription{}
.set_name(implicit_layer_name)
.set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)
.set_disable_environment(disable_env_var.get())
.set_enable_environment(enable_env_var.get())),
"implicit_test_layer.json");
auto layers = env.GetLayerProperties(1);
ASSERT_TRUE(string_eq(layers[0].layerName, implicit_layer_name));
// didn't set enable env-var, layer should not load
CheckLogForLayerString(env, implicit_layer_name, false);
// set enable env-var to 0, no layer should be found
enable_env_var.set_new_value("0");
CheckLogForLayerString(env, implicit_layer_name, false);
// set enable env-var, layer should load
enable_env_var.set_new_value("1");
CheckLogForLayerString(env, implicit_layer_name, true);
// remove enable env var, so we can check what happens when only disable is present
enable_env_var.remove_value();
// set disable env-var to 0, layer should not load
disable_env_var.set_new_value("0");
CheckLogForLayerString(env, implicit_layer_name, false);
// set disable env-var to 1, layer should not load
disable_env_var.set_new_value("1");
CheckLogForLayerString(env, implicit_layer_name, false);
// set both enable and disable env-var, layer should not load
enable_env_var.set_new_value("1");
disable_env_var.set_new_value("1");
CheckLogForLayerString(env, implicit_layer_name, false);
}
TEST(ImplicitLayers, OnlyDisableEnvVar) {
FrameworkEnvironment env;
env.add_icd(TestICDDetails(TEST_ICD_PATH_VERSION_2_EXPORT_ICD_GPDPA));
const char* implicit_layer_name = "VK_LAYER_ImplicitTestLayer";
EnvVarWrapper disable_env_var{"DISABLE_ME"};
env.add_implicit_layer(ManifestLayer{}.add_layer(ManifestLayer::LayerDescription{}
.set_name(implicit_layer_name)
.set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)
.set_disable_environment(disable_env_var.get())),
"implicit_test_layer.json");
auto layers = env.GetLayerProperties(1);
ASSERT_TRUE(string_eq(layers[0].layerName, implicit_layer_name));
// don't set disable env-var, layer should load
CheckLogForLayerString(env, implicit_layer_name, true);
// set disable env-var to 0, layer should load
disable_env_var.set_new_value("0");
CheckLogForLayerString(env, implicit_layer_name, false);
// set disable env-var to 1, layer should not load
disable_env_var.set_new_value("1");
CheckLogForLayerString(env, implicit_layer_name, false);
{
InstWrapper inst{env.vulkan_functions};
FillDebugUtilsCreateDetails(inst.create_info, env.debug_log);
inst.create_info.add_layer(implicit_layer_name);
inst.CheckCreate(VK_SUCCESS);
ASSERT_TRUE(env.debug_log.find(std::string("Insert instance layer \"") + implicit_layer_name));
}
}
TEST(ImplicitLayers, PreInstanceEnumInstLayerProps) {
FrameworkEnvironment env;
env.add_icd(TestICDDetails(TEST_ICD_PATH_VERSION_2_EXPORT_ICD_GPDPA));
const char* implicit_layer_name = "VK_LAYER_ImplicitTestLayer";
EnvVarWrapper disable_env_var{"DISABLE_ME"};
env.add_implicit_layer(
ManifestLayer{}.set_file_format_version({1, 1, 2}).add_layer(
ManifestLayer::LayerDescription{}
.set_name(implicit_layer_name)
.set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)
.set_disable_environment(disable_env_var.get())
.add_pre_instance_function(ManifestLayer::LayerDescription::FunctionOverride{}
.set_vk_func("vkEnumerateInstanceLayerProperties")
.set_override_name("test_preinst_vkEnumerateInstanceLayerProperties"))),
"implicit_test_layer.json");
uint32_t layer_props = 43;
auto& layer = env.get_test_layer(0);
layer.set_reported_layer_props(layer_props);
uint32_t count = 0;
ASSERT_EQ(VK_SUCCESS, env.vulkan_functions.vkEnumerateInstanceLayerProperties(&count, nullptr));
ASSERT_EQ(count, layer_props);
// set disable env-var to 1, layer should not load
disable_env_var.set_new_value("1");
count = 0;
ASSERT_EQ(VK_SUCCESS, env.vulkan_functions.vkEnumerateInstanceLayerProperties(&count, nullptr));
ASSERT_NE(count, 0U);
ASSERT_NE(count, layer_props);
}
TEST(ImplicitLayers, PreInstanceEnumInstExtProps) {
FrameworkEnvironment env;
env.add_icd(TestICDDetails(TEST_ICD_PATH_VERSION_2_EXPORT_ICD_GPDPA));
const char* implicit_layer_name = "VK_LAYER_ImplicitTestLayer";
EnvVarWrapper disable_env_var{"DISABLE_ME"};
env.add_implicit_layer(
ManifestLayer{}.set_file_format_version({1, 1, 2}).add_layer(
ManifestLayer::LayerDescription{}
.set_name(implicit_layer_name)
.set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)
.set_disable_environment(disable_env_var.get())
.add_pre_instance_function(ManifestLayer::LayerDescription::FunctionOverride{}
.set_vk_func("vkEnumerateInstanceExtensionProperties")
.set_override_name("test_preinst_vkEnumerateInstanceExtensionProperties"))),
"implicit_test_layer.json");
uint32_t ext_props = 52;
auto& layer = env.get_test_layer(0);
layer.set_reported_extension_props(ext_props);
uint32_t count = 0;
ASSERT_EQ(VK_SUCCESS, env.vulkan_functions.vkEnumerateInstanceExtensionProperties(nullptr, &count, nullptr));
ASSERT_EQ(count, ext_props);
// set disable env-var to 1, layer should not load
disable_env_var.set_new_value("1");
count = 0;
ASSERT_EQ(VK_SUCCESS, env.vulkan_functions.vkEnumerateInstanceExtensionProperties(nullptr, &count, nullptr));
ASSERT_NE(count, 0U);
ASSERT_NE(count, ext_props);
}
TEST(ImplicitLayers, PreInstanceVersion) {
FrameworkEnvironment env;
env.add_icd(TestICDDetails(TEST_ICD_PATH_VERSION_2_EXPORT_ICD_GPDPA))
.add_physical_device({})
.set_icd_api_version(VK_MAKE_API_VERSION(0, 1, 2, 3));
const char* implicit_layer_name = "VK_LAYER_ImplicitTestLayer";
EnvVarWrapper disable_env_var{"DISABLE_ME"};
env.add_implicit_layer(ManifestLayer{}.set_file_format_version({1, 1, 2}).add_layer(
ManifestLayer::LayerDescription{}
.set_name(implicit_layer_name)
.set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)
.set_api_version(VK_MAKE_API_VERSION(0, 1, 2, 3))
.set_disable_environment(disable_env_var.get())
.add_pre_instance_function(ManifestLayer::LayerDescription::FunctionOverride{}
.set_vk_func("vkEnumerateInstanceVersion")
.set_override_name("test_preinst_vkEnumerateInstanceVersion"))),
"implicit_test_layer.json");
uint32_t layer_version = VK_MAKE_API_VERSION(1, 2, 3, 4);
auto& layer = env.get_test_layer(0);
layer.set_reported_instance_version(layer_version);
uint32_t version = 0;
ASSERT_EQ(VK_SUCCESS, env.vulkan_functions.vkEnumerateInstanceVersion(&version));
ASSERT_EQ(version, layer_version);
// set disable env-var to 1, layer should not load
disable_env_var.set_new_value("1");
version = 0;
ASSERT_EQ(VK_SUCCESS, env.vulkan_functions.vkEnumerateInstanceVersion(&version));
ASSERT_NE(version, 0U);
ASSERT_NE(version, layer_version);
}
// Run with a pre-Negotiate function version of the layer so that it has to query vkCreateInstance using the
// renamed vkGetInstanceProcAddr function which returns one that intentionally fails. Then disable the
// layer and verify it works. The non-override version of vkCreateInstance in the layer also works (and is
// tested through behavior above).
TEST(ImplicitLayers, OverrideGetInstanceProcAddr) {
FrameworkEnvironment env;
env.add_icd(TestICDDetails(TEST_ICD_PATH_VERSION_2_EXPORT_ICD_GPDPA)).add_physical_device({});
const char* implicit_layer_name = "VK_LAYER_ImplicitTestLayer";
EnvVarWrapper disable_env_var{"DISABLE_ME"};
env.add_implicit_layer(ManifestLayer{}.set_file_format_version({1, 0, 0}).add_layer(
ManifestLayer::LayerDescription{}
.set_name(implicit_layer_name)
.set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_1)
.set_disable_environment(disable_env_var.get())
.add_function(ManifestLayer::LayerDescription::FunctionOverride{}
.set_vk_func("vkGetInstanceProcAddr")
.set_override_name("test_override_vkGetInstanceProcAddr"))),
"implicit_test_layer.json");
{
InstWrapper inst1{env.vulkan_functions};
inst1.CheckCreate(VK_ERROR_INVALID_SHADER_NV);
}
{
// set disable env-var to 1, layer should not load
disable_env_var.set_new_value("1");
InstWrapper inst2{env.vulkan_functions};
inst2.CheckCreate();
}
}
// Force enable with filter env var
TEST(ImplicitLayers, EnableWithFilter) {
FrameworkEnvironment env;
env.add_icd(TestICDDetails(TEST_ICD_PATH_VERSION_2_EXPORT_ICD_GPDPA))
.add_physical_device({})
.set_icd_api_version(VK_API_VERSION_1_2);
const char* implicit_layer_name_1 = "VK_LAYER_LUNARG_First_layer";
const char* implicit_json_name_1 = "First_layer.json";
const char* disable_layer_name_1 = "DISABLE_FIRST";
const char* enable_layer_name_1 = "ENABLE_FIRST";
env.add_implicit_layer(ManifestLayer{}.add_layer(ManifestLayer::LayerDescription{}
.set_name(implicit_layer_name_1)
.set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)
.set_enable_environment(enable_layer_name_1)
.set_disable_environment(disable_layer_name_1)
.set_api_version(VK_MAKE_API_VERSION(0, 1, 0, 0))),
implicit_json_name_1);
const char* implicit_layer_name_2 = "VK_LAYER_LUNARG_Second_layer";
const char* implicit_json_name_2 = "Second_layer.json";
const char* disable_layer_name_2 = "DISABLE_SECOND";
const char* enable_layer_name_2 = "ENABLE_SECOND";
env.add_implicit_layer(ManifestLayer{}.add_layer(ManifestLayer::LayerDescription{}
.set_name(implicit_layer_name_2)
.set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)
.set_enable_environment(enable_layer_name_2)
.set_disable_environment(disable_layer_name_2)
.set_api_version(VK_MAKE_API_VERSION(0, 1, 0, 0))),
implicit_json_name_2);
const char* implicit_layer_name_3 = "VK_LAYER_LUNARG_Second_test_layer";
const char* implicit_json_name_3 = "Second_test_layer.json";
const char* disable_layer_name_3 = "DISABLE_THIRD";
const char* enable_layer_name_3 = "ENABLE_THIRD";
env.add_implicit_layer(ManifestLayer{}.add_layer(ManifestLayer::LayerDescription{}
.set_name(implicit_layer_name_3)
.set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)
.set_enable_environment(enable_layer_name_3)
.set_disable_environment(disable_layer_name_3)
.set_api_version(VK_MAKE_API_VERSION(0, 1, 0, 0))),
implicit_json_name_3);
EnvVarWrapper layers_enable_env_var{"VK_LOADER_LAYERS_ENABLE"};
EnvVarWrapper layer_1_enable_env_var{enable_layer_name_1};
// First, test an instance/device without the layer forced on.
InstWrapper inst1{env.vulkan_functions};
FillDebugUtilsCreateDetails(inst1.create_info, env.debug_log);
inst1.CheckCreate();
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_1));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_1));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_1, "forced enabled due to env var"));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_1, "disabled because name matches filter of env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_2));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_2));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_2, "forced enabled due to env var"));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_2, "disabled because name matches filter of env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_3));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_3));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_3, "forced enabled due to env var"));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_3, "disabled because name matches filter of env var"));
// Now force on one layer with its full name
// ------------------------------------------
env.debug_log.clear();
layers_enable_env_var.set_new_value(implicit_layer_name_1);
InstWrapper inst2{env.vulkan_functions};
FillDebugUtilsCreateDetails(inst2.create_info, env.debug_log);
inst2.CheckCreate();
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_1));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_1));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_1, "forced enabled due to env var"));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_1, "disabled because name matches filter of env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_2));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_2));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_2, "forced enabled due to env var"));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_2, "disabled because name matches filter of env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_3));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_3));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_3, "forced enabled due to env var"));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_3, "disabled because name matches filter of env var"));
// Match prefix
// ------------------------------------------
env.debug_log.clear();
layers_enable_env_var.set_new_value("VK_LAYER_LUNARG_*");
InstWrapper inst3{env.vulkan_functions};
FillDebugUtilsCreateDetails(inst3.create_info, env.debug_log);
inst3.CheckCreate();
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_1));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_1));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_1, "forced enabled due to env var"));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_1, "disabled because name matches filter of env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_2));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_2));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_2, "forced enabled due to env var"));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_2, "disabled because name matches filter of env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_3));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_3));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_3, "forced enabled due to env var"));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_3, "disabled because name matches filter of env var"));
// Match suffix
// ------------------------------------------
env.debug_log.clear();
layers_enable_env_var.set_new_value("*Second_layer");
InstWrapper inst4{env.vulkan_functions};
FillDebugUtilsCreateDetails(inst4.create_info, env.debug_log);
inst4.CheckCreate();
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_1));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_1));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_1, "forced enabled due to env var"));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_1, "disabled because name matches filter of env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_2));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_2));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_2, "forced enabled due to env var"));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_2, "disabled because name matches filter of env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_3));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_3));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_3, "forced enabled due to env var"));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_3, "disabled because name matches filter of env var"));
// Match substring
// ------------------------------------------
env.debug_log.clear();
layers_enable_env_var.set_new_value("*Second*");
InstWrapper inst5{env.vulkan_functions};
FillDebugUtilsCreateDetails(inst5.create_info, env.debug_log);
inst5.CheckCreate();
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_1));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_1));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_1, "forced enabled due to env var"));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_1, "disabled because name matches filter of env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_2));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_2));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_2, "forced enabled due to env var"));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_2, "disabled because name matches filter of env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_3));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_3));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_3, "forced enabled due to env var"));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_3, "disabled because name matches filter of env var"));
// Match all with star '*'
// ------------------------------------------
env.debug_log.clear();
layers_enable_env_var.set_new_value("*");
InstWrapper inst6{env.vulkan_functions};
FillDebugUtilsCreateDetails(inst6.create_info, env.debug_log);
inst6.CheckCreate();
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_1));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_1));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_1, "forced enabled due to env var"));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_1, "disabled because name matches filter of env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_2));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_2));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_2, "forced enabled due to env var"));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_2, "disabled because name matches filter of env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_3));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_3));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_3, "forced enabled due to env var"));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_3, "disabled because name matches filter of env var"));
// Match all with special name
// ------------------------------------------
env.debug_log.clear();
layers_enable_env_var.set_new_value("~all~");
InstWrapper inst7{env.vulkan_functions};
FillDebugUtilsCreateDetails(inst7.create_info, env.debug_log);
inst7.CheckCreate();
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_1));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_1));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_1, "forced enabled due to env var"));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_1, "disabled because name matches filter of env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_2));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_2));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_2, "forced enabled due to env var"));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_2, "disabled because name matches filter of env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_3));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_3));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_3, "forced enabled due to env var"));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_3, "disabled because name matches filter of env var"));
// Match substring, but enable the other layer manually
// ------------------------------------------
env.debug_log.clear();
layer_1_enable_env_var.set_new_value("1");
layers_enable_env_var.set_new_value("*Second*");
InstWrapper inst8{env.vulkan_functions};
FillDebugUtilsCreateDetails(inst8.create_info, env.debug_log);
inst8.CheckCreate();
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_1));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_1));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_1, "forced enabled due to env var"));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_1, "disabled because name matches filter of env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_2));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_2));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_2, "forced enabled due to env var"));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_2, "disabled because name matches filter of env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_3));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_3));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_3, "forced enabled due to env var"));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_3, "disabled because name matches filter of env var"));
}
// Force disabled with new filter env var
TEST(ImplicitLayers, DisableWithFilter) {
FrameworkEnvironment env;
env.add_icd(TestICDDetails(TEST_ICD_PATH_VERSION_2_EXPORT_ICD_GPDPA, VK_API_VERSION_1_2))
.set_icd_api_version(VK_API_VERSION_1_2);
const char* implicit_layer_name_1 = "VK_LAYER_LUNARG_First_layer";
const char* implicit_json_name_1 = "First_layer.json";
const char* disable_layer_name_1 = "DISABLE_FIRST";
env.add_implicit_layer(ManifestLayer{}.add_layer(ManifestLayer::LayerDescription{}
.set_name(implicit_layer_name_1)
.set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)
.set_disable_environment(disable_layer_name_1)
.set_api_version(VK_MAKE_API_VERSION(0, 1, 0, 0))),
implicit_json_name_1);
const char* implicit_layer_name_2 = "VK_LAYER_LUNARG_Second_layer";
const char* implicit_json_name_2 = "Second_layer.json";
const char* disable_layer_name_2 = "DISABLE_SECOND";
env.add_implicit_layer(ManifestLayer{}.add_layer(ManifestLayer::LayerDescription{}
.set_name(implicit_layer_name_2)
.set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)
.set_disable_environment(disable_layer_name_2)
.set_api_version(VK_MAKE_API_VERSION(0, 1, 0, 0))),
implicit_json_name_2);
const char* implicit_layer_name_3 = "VK_LAYER_LUNARG_Second_test_layer";
const char* implicit_json_name_3 = "Second_test_layer.json";
const char* disable_layer_name_3 = "DISABLE_THIRD";
env.add_implicit_layer(ManifestLayer{}.add_layer(ManifestLayer::LayerDescription{}
.set_name(implicit_layer_name_3)
.set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)
.set_disable_environment(disable_layer_name_3)
.set_api_version(VK_MAKE_API_VERSION(0, 1, 0, 0))),
implicit_json_name_3);
EnvVarWrapper layers_disable_env_var{"VK_LOADER_LAYERS_DISABLE"};
// First, test an instance/device
InstWrapper inst1{env.vulkan_functions};
FillDebugUtilsCreateDetails(inst1.create_info, env.debug_log);
inst1.CheckCreate();
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_1));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_1));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_1, "forced enabled due to env var"));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_1, "disabled because name matches filter of env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_2));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_2));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_2, "forced enabled due to env var"));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_2, "disabled because name matches filter of env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_3));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_3));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_3, "forced enabled due to env var"));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_3, "disabled because name matches filter of env var"));
// Now force off one layer with its full name
// ------------------------------------------
env.debug_log.clear();
layers_disable_env_var.set_new_value(implicit_layer_name_1);
InstWrapper inst2{env.vulkan_functions};
FillDebugUtilsCreateDetails(inst2.create_info, env.debug_log);
inst2.CheckCreate();
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_1));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_1));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_1, "forced enabled due to env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_1, "disabled because name matches filter of env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_2));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_2));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_2, "forced enabled due to env var"));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_2, "disabled because name matches filter of env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_3));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_3));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_3, "forced enabled due to env var"));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_3, "disabled because name matches filter of env var"));
// Match prefix
// ------------------------------------------
env.debug_log.clear();
layers_disable_env_var.set_new_value("VK_LAYER_LUNARG_*");
InstWrapper inst3{env.vulkan_functions};
FillDebugUtilsCreateDetails(inst3.create_info, env.debug_log);
inst3.CheckCreate();
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_1));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_1));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_1, "forced enabled due to env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_1, "disabled because name matches filter of env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_2));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_2));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_2, "forced enabled due to env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_2, "disabled because name matches filter of env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_3));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_3));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_3, "forced enabled due to env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_3, "disabled because name matches filter of env var"));
// Match suffix
// ------------------------------------------
env.debug_log.clear();
layers_disable_env_var.set_new_value("*Second_layer");
InstWrapper inst4{env.vulkan_functions};
FillDebugUtilsCreateDetails(inst4.create_info, env.debug_log);
inst4.CheckCreate();
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_1));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_1));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_1, "forced enabled due to env var"));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_1, "disabled because name matches filter of env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_2));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_2));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_2, "forced enabled due to env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_2, "disabled because name matches filter of env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_3));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_3));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_3, "forced enabled due to env var"));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_3, "disabled because name matches filter of env var"));
// Match substring
// ------------------------------------------
env.debug_log.clear();
layers_disable_env_var.set_new_value("*Second*");
InstWrapper inst5{env.vulkan_functions};
FillDebugUtilsCreateDetails(inst5.create_info, env.debug_log);
inst5.CheckCreate();
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_1));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_1));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_1, "forced enabled due to env var"));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_1, "disabled because name matches filter of env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_2));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_2));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_2, "forced enabled due to env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_2, "disabled because name matches filter of env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_3));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_3));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_3, "forced enabled due to env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_3, "disabled because name matches filter of env var"));
// Match all with star '*'
// ------------------------------------------
env.debug_log.clear();
layers_disable_env_var.set_new_value("*");
InstWrapper inst6{env.vulkan_functions};
FillDebugUtilsCreateDetails(inst6.create_info, env.debug_log);
inst6.CheckCreate();
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_1));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_1));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_1, "forced enabled due to env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_1, "disabled because name matches filter of env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_2));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_2));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_2, "forced enabled due to env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_2, "disabled because name matches filter of env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_3));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_3));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_3, "forced enabled due to env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_3, "disabled because name matches filter of env var"));
// Match all with special name
// ------------------------------------------
env.debug_log.clear();
layers_disable_env_var.set_new_value("~all~");
InstWrapper inst7{env.vulkan_functions};
FillDebugUtilsCreateDetails(inst7.create_info, env.debug_log);
inst7.CheckCreate();
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_1));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_1));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_1, "forced enabled due to env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_1, "disabled because name matches filter of env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_2));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_2));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_2, "forced enabled due to env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_2, "disabled because name matches filter of env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_3));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_3));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_3, "forced enabled due to env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_3, "disabled because name matches filter of env var"));
}
// Force disabled with new filter env var
TEST(ImplicitLayers, DisableWithFilterWhenLayersEnableEnvVarIsActive) {
FrameworkEnvironment env;
env.add_icd(TestICDDetails(TEST_ICD_PATH_VERSION_2_EXPORT_ICD_GPDPA, VK_API_VERSION_1_2))
.set_icd_api_version(VK_API_VERSION_1_2);
const char* implicit_layer_name_1 = "VK_LAYER_LUNARG_First_layer";
const char* implicit_json_name_1 = "First_layer.json";
const char* disable_layer_name_1 = "DISABLE_FIRST";
const char* enable_layer_name_1 = "ENABLE_FIRST";
env.add_implicit_layer(ManifestLayer{}.add_layer(ManifestLayer::LayerDescription{}
.set_name(implicit_layer_name_1)
.set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)
.set_disable_environment(disable_layer_name_1)
.set_enable_environment(enable_layer_name_1)
.set_api_version(VK_MAKE_API_VERSION(0, 1, 0, 0))),
implicit_json_name_1);
const char* implicit_layer_name_2 = "VK_LAYER_LUNARG_Second_layer";
const char* implicit_json_name_2 = "Second_layer.json";
const char* disable_layer_name_2 = "DISABLE_SECOND";
const char* enable_layer_name_2 = "ENABLE_SECOND";
env.add_implicit_layer(ManifestLayer{}.add_layer(ManifestLayer::LayerDescription{}
.set_name(implicit_layer_name_2)
.set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)
.set_disable_environment(disable_layer_name_2)
.set_enable_environment(enable_layer_name_2)
.set_api_version(VK_MAKE_API_VERSION(0, 1, 0, 0))),
implicit_json_name_2);
EnvVarWrapper layers_disable_env_var{"VK_LOADER_LAYERS_DISABLE"};
EnvVarWrapper layer_1_enable_env_var{enable_layer_name_1};
EnvVarWrapper layer_2_enable_env_var{enable_layer_name_2};
// First, test an instance/device
InstWrapper inst1{env.vulkan_functions};
FillDebugUtilsCreateDetails(inst1.create_info, env.debug_log);
inst1.CheckCreate();
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_1));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_1));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_1, "forced enabled due to env var"));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_1, "disabled because name matches filter of env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_2));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_2));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_2, "forced enabled due to env var"));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_2, "disabled because name matches filter of env var"));
// Set the layers enable env-var
// ------------------------------------------
env.debug_log.clear();
layer_1_enable_env_var.set_new_value("1");
layer_2_enable_env_var.set_new_value("1");
InstWrapper inst2{env.vulkan_functions};
FillDebugUtilsCreateDetails(inst2.create_info, env.debug_log);
inst2.CheckCreate();
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_1));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_1));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_1, "forced enabled due to env var"));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_1, "disabled because name matches filter of env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_2));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_2));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_2, "forced enabled due to env var"));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_2, "disabled because name matches filter of env var"));
// Now force off one layer with its full name
// ------------------------------------------
env.debug_log.clear();
layers_disable_env_var.set_new_value(implicit_layer_name_1);
InstWrapper inst3{env.vulkan_functions};
FillDebugUtilsCreateDetails(inst3.create_info, env.debug_log);
inst3.CheckCreate();
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_1));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_1));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_1, "forced enabled due to env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_1, "disabled because name matches filter of env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_2));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_2));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_2, "forced enabled due to env var"));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_2, "disabled because name matches filter of env var"));
// Now force off both layers
// ------------------------------------------
env.debug_log.clear();
layers_disable_env_var.set_new_value("~implicit~");
InstWrapper inst4{env.vulkan_functions};
FillDebugUtilsCreateDetails(inst4.create_info, env.debug_log);
inst4.CheckCreate();
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_1));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_1));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_1, "forced enabled due to env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_1, "disabled because name matches filter of env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_2));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_2));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_2, "forced enabled due to env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_2, "disabled because name matches filter of env var"));
}
// Test interaction between both the enable and disable filter environment variables. The enable should always
// override the disable.
TEST(ImplicitLayers, EnableAndDisableWithFilter) {
FrameworkEnvironment env;
env.add_icd(TestICDDetails(TEST_ICD_PATH_VERSION_2_EXPORT_ICD_GPDPA, VK_API_VERSION_1_2))
.set_icd_api_version(VK_API_VERSION_1_2);
const char* implicit_layer_name_1 = "VK_LAYER_LUNARG_First_layer";
const char* implicit_json_name_1 = "First_layer.json";
const char* disable_layer_name_1 = "DISABLE_FIRST";
env.add_implicit_layer(ManifestLayer{}.add_layer(ManifestLayer::LayerDescription{}
.set_name(implicit_layer_name_1)
.set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)
.set_disable_environment(disable_layer_name_1)
.set_api_version(VK_MAKE_API_VERSION(0, 1, 0, 0))),
implicit_json_name_1);
const char* implicit_layer_name_2 = "VK_LAYER_LUNARG_Second_layer";
const char* implicit_json_name_2 = "Second_layer.json";
const char* disable_layer_name_2 = "DISABLE_SECOND";
env.add_implicit_layer(ManifestLayer{}.add_layer(ManifestLayer::LayerDescription{}
.set_name(implicit_layer_name_2)
.set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)
.set_disable_environment(disable_layer_name_2)
.set_api_version(VK_MAKE_API_VERSION(0, 1, 0, 0))),
implicit_json_name_2);
const char* implicit_layer_name_3 = "VK_LAYER_LUNARG_Second_test_layer";
const char* implicit_json_name_3 = "Second_test_layer.json";
const char* disable_layer_name_3 = "DISABLE_THIRD";
env.add_implicit_layer(ManifestLayer{}.add_layer(ManifestLayer::LayerDescription{}
.set_name(implicit_layer_name_3)
.set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)
.set_disable_environment(disable_layer_name_3)
.set_api_version(VK_MAKE_API_VERSION(0, 1, 0, 0))),
implicit_json_name_3);
EnvVarWrapper layers_disable_env_var{"VK_LOADER_LAYERS_DISABLE"};
EnvVarWrapper layers_enable_env_var{"VK_LOADER_LAYERS_ENABLE"};
// Disable 2 but enable 1
// ------------------------------------------
env.debug_log.clear();
layers_disable_env_var.set_new_value("*Second*");
layers_enable_env_var.set_new_value("*test_layer");
InstWrapper inst1{env.vulkan_functions};
FillDebugUtilsCreateDetails(inst1.create_info, env.debug_log);
inst1.CheckCreate();
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_1));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_1));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_1, "forced enabled due to env var"));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_1, "disabled because name matches filter of env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_2));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_2));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_2, "forced enabled due to env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_2, "disabled because name matches filter of env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_3));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_3));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_3, "forced enabled due to env var"));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_3, "disabled because name matches filter of env var"));
// Disable all but enable 2
// ------------------------------------------
env.debug_log.clear();
layers_disable_env_var.set_new_value("*");
layers_enable_env_var.set_new_value("*Second*");
InstWrapper inst2{env.vulkan_functions};
FillDebugUtilsCreateDetails(inst2.create_info, env.debug_log);
inst2.CheckCreate();
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_1));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_1));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_1, "forced enabled due to env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_1, "disabled because name matches filter of env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_2));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_2));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_2, "forced enabled due to env var"));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_2, "disabled because name matches filter of env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_3));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_3));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_3, "forced enabled due to env var"));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_3, "disabled because name matches filter of env var"));
// Disable all but enable 2
// ------------------------------------------
env.debug_log.clear();
layers_disable_env_var.set_new_value("~all~");
layers_enable_env_var.set_new_value("*Second*");
InstWrapper inst3{env.vulkan_functions};
FillDebugUtilsCreateDetails(inst3.create_info, env.debug_log);
inst3.CheckCreate();
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_1));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_1));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_1, "forced enabled due to env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_1, "disabled because name matches filter of env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_2));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_2));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_2, "forced enabled due to env var"));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_2, "disabled because name matches filter of env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_3));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_3));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_3, "forced enabled due to env var"));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_3, "disabled because name matches filter of env var"));
// Disable implicit but enable 2
// ------------------------------------------
env.debug_log.clear();
layers_disable_env_var.set_new_value("~implicit~");
layers_enable_env_var.set_new_value("*Second*");
InstWrapper inst4{env.vulkan_functions};
FillDebugUtilsCreateDetails(inst4.create_info, env.debug_log);
inst4.CheckCreate();
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_1));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_1));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_1, "forced enabled due to env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_1, "disabled because name matches filter of env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_2));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_2));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_2, "forced enabled due to env var"));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_2, "disabled because name matches filter of env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_3));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_3));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_3, "forced enabled due to env var"));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_3, "disabled because name matches filter of env var"));
// Disable explicit but enable 2 (should still be everything)
// ------------------------------------------
env.debug_log.clear();
layers_disable_env_var.set_new_value("~explicit~");
layers_enable_env_var.set_new_value("*Second*");
InstWrapper inst5{env.vulkan_functions};
FillDebugUtilsCreateDetails(inst5.create_info, env.debug_log);
inst5.CheckCreate();
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_1));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_1));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_1, "forced enabled due to env var"));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_1, "disabled because name matches filter of env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_2));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_2));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_2, "forced enabled due to env var"));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_2, "disabled because name matches filter of env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_3));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_3));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_3, "forced enabled due to env var"));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_3, "disabled because name matches filter of env var"));
// Disable implicit but enable all
// ------------------------------------------
env.debug_log.clear();
layers_disable_env_var.set_new_value("~implicit~");
layers_enable_env_var.set_new_value("*");
InstWrapper inst6{env.vulkan_functions};
FillDebugUtilsCreateDetails(inst6.create_info, env.debug_log);
inst6.CheckCreate();
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_1));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_1));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_1, "forced enabled due to env var"));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_1, "disabled because name matches filter of env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_2));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_2));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_2, "forced enabled due to env var"));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_2, "disabled because name matches filter of env var"));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Found manifest file", implicit_json_name_3));
ASSERT_TRUE(env.debug_log.find_prefix_then_postfix("Insert instance layer", implicit_layer_name_3));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_3, "forced enabled due to env var"));
ASSERT_FALSE(env.debug_log.find_prefix_then_postfix(implicit_layer_name_3, "disabled because name matches filter of env var"));
}
// Add 2 implicit layers with the same layer name and expect only one to be loaded.
// Expect the second layer to be found first, because it'll be in a path that is searched first.
TEST(ImplicitLayers, DuplicateLayers) {
FrameworkEnvironment env;
env.add_icd(TestICDDetails(TEST_ICD_PATH_VERSION_2_EXPORT_ICD_GPDPA)).add_physical_device({});
// verify layer loads successfully when setting VK_LAYER_PATH to a full filepath
const char* same_layer_name_1 = "VK_LAYER_RegularLayer1";
env.add_implicit_layer(TestLayerDetails(ManifestLayer{}.add_layer(ManifestLayer::LayerDescription{}
.set_name(same_layer_name_1)
.set_description("actually_layer_1")
.set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)
.set_disable_environment("if_you_can")),
"regular_layer_1.json"));
auto& layer1 = env.get_test_layer(0);
layer1.set_description("actually_layer_1");
layer1.set_make_spurious_log_in_create_instance("actually_layer_1");
env.add_implicit_layer(TestLayerDetails(ManifestLayer{}.add_layer(ManifestLayer::LayerDescription{}
.set_name(same_layer_name_1)
.set_description("actually_layer_2")
.set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)
.set_disable_environment("if_you_can")),
"regular_layer_1.json")
// use override folder as just a folder and manually add it to the implicit layer search paths
.set_discovery_type(ManifestDiscoveryType::override_folder));
auto& layer2 = env.get_test_layer(1);
layer2.set_description("actually_layer_2");
layer2.set_make_spurious_log_in_create_instance("actually_layer_2");
#if defined(WIN32)
env.platform_shim->add_manifest(ManifestCategory::implicit_layer, env.get_folder(ManifestLocation::override_layer).location());
#elif COMMON_UNIX_PLATFORMS
env.platform_shim->redirect_path(std::filesystem::path(USER_LOCAL_SHARE_DIR "/vulkan/implicit_layer.d"),
env.get_folder(ManifestLocation::override_layer).location());
#endif
auto layer_props = env.GetLayerProperties(2);
ASSERT_TRUE(string_eq(same_layer_name_1, layer_props[0].layerName));
ASSERT_TRUE(string_eq(same_layer_name_1, layer_props[1].layerName));
ASSERT_TRUE(string_eq(layer1.description.c_str(), layer_props[0].description));
ASSERT_TRUE(string_eq(layer2.description.c_str(), layer_props[1].description));
InstWrapper inst{env.vulkan_functions};
FillDebugUtilsCreateDetails(inst.create_info, env.debug_log);
inst.CheckCreate();
auto enabled_layer_props = inst.GetActiveLayers(inst.GetPhysDev(), 1);
ASSERT_TRUE(string_eq(same_layer_name_1, enabled_layer_props.at(0).layerName));
ASSERT_TRUE(string_eq(layer1.description.c_str(), enabled_layer_props.at(0).description));
ASSERT_TRUE(env.debug_log.find("actually_layer_1"));
ASSERT_FALSE(env.debug_log.find("actually_layer_2"));
}
// Meta layer which contains component layers that do not exist.
TEST(MetaLayers, InvalidComponentLayer) {
FrameworkEnvironment env;
env.add_icd(TestICDDetails(TEST_ICD_PATH_VERSION_2_EXPORT_ICD_GPDPA));
const char* meta_layer_name = "VK_LAYER_MetaTestLayer";
const char* invalid_layer_name_1 = "VK_LAYER_InvalidLayer1";
const char* invalid_layer_name_2 = "VK_LAYER_InvalidLayer2";
env.add_implicit_layer(ManifestLayer{}.set_file_format_version({1, 1, 2}).add_layer(
ManifestLayer::LayerDescription{}
.set_name(meta_layer_name)
.add_component_layers({invalid_layer_name_1, invalid_layer_name_2})
.set_disable_environment("NotGonnaWork")
.add_instance_extension({"NeverGonnaGiveYouUp"})
.add_device_extension({"NeverGonnaLetYouDown"})),
"meta_test_layer.json");
const char* regular_layer_name = "TestLayer";
env.add_explicit_layer(
ManifestLayer{}.add_layer(
ManifestLayer::LayerDescription{}.set_name(regular_layer_name).set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)),
"regular_test_layer.json");
// should find 1, the 'regular' layer
auto layer_props = env.GetLayerProperties(1);
EXPECT_TRUE(string_eq(layer_props.at(0).layerName, regular_layer_name));
auto extensions = env.GetInstanceExtensions(4);
EXPECT_TRUE(string_eq(extensions.at(0).extensionName, VK_EXT_DEBUG_REPORT_EXTENSION_NAME));
EXPECT_TRUE(string_eq(extensions.at(1).extensionName, VK_EXT_DEBUG_UTILS_EXTENSION_NAME));
EXPECT_TRUE(string_eq(extensions.at(2).extensionName, VK_KHR_PORTABILITY_ENUMERATION_EXTENSION_NAME));
EXPECT_TRUE(string_eq(extensions.at(3).extensionName, VK_LUNARG_DIRECT_DRIVER_LOADING_EXTENSION_NAME));
InstWrapper inst{env.vulkan_functions};
inst.create_info.add_layer(meta_layer_name);
FillDebugUtilsCreateDetails(inst.create_info, env.debug_log);
inst.CheckCreate(VK_ERROR_LAYER_NOT_PRESENT);
ASSERT_TRUE(env.debug_log.find(std::string("verify_meta_layer_component_layers: Meta-layer ") + meta_layer_name +
" can't find component layer " + invalid_layer_name_1 + " at index 0. Skipping this layer."));
}
// Meta layer that is an explicit layer
TEST(MetaLayers, ExplicitMetaLayer) {
FrameworkEnvironment env;
env.add_icd(TestICDDetails(TEST_ICD_PATH_VERSION_2_EXPORT_ICD_GPDPA)).add_physical_device({});
const char* meta_layer_name = "VK_LAYER_MetaTestLayer";
const char* regular_layer_name = "VK_LAYER_TestLayer";
env.add_explicit_layer(
ManifestLayer{}.set_file_format_version({1, 1, 2}).add_layer(
ManifestLayer::LayerDescription{}.set_name(meta_layer_name).add_component_layers({regular_layer_name})),
"meta_test_layer.json");
env.add_explicit_layer(
ManifestLayer{}.add_layer(
ManifestLayer::LayerDescription{}.set_name(regular_layer_name).set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)),
"regular_test_layer.json");
{ // global functions
// should find 1, the 'regular' layer
auto layer_props = env.GetLayerProperties(2);
EXPECT_TRUE(check_permutation({regular_layer_name, meta_layer_name}, layer_props));
auto extensions = env.GetInstanceExtensions(4);
EXPECT_TRUE(string_eq(extensions.at(0).extensionName, VK_EXT_DEBUG_REPORT_EXTENSION_NAME));
EXPECT_TRUE(string_eq(extensions.at(1).extensionName, VK_EXT_DEBUG_UTILS_EXTENSION_NAME));
EXPECT_TRUE(string_eq(extensions.at(2).extensionName, VK_KHR_PORTABILITY_ENUMERATION_EXTENSION_NAME));
EXPECT_TRUE(string_eq(extensions.at(3).extensionName, VK_LUNARG_DIRECT_DRIVER_LOADING_EXTENSION_NAME));
}
{ // don't enable the layer, shouldn't find any layers when calling vkEnumerateDeviceLayerProperties
InstWrapper inst{env.vulkan_functions};
inst.CheckCreate(VK_SUCCESS);
ASSERT_NO_FATAL_FAILURE(inst.GetActiveLayers(inst.GetPhysDev(), 0));
}
{
InstWrapper inst{env.vulkan_functions};
inst.create_info.add_layer(meta_layer_name);
inst.CheckCreate(VK_SUCCESS);
auto layer_props = inst.GetActiveLayers(inst.GetPhysDev(), 2);
EXPECT_TRUE(check_permutation({regular_layer_name, meta_layer_name}, layer_props));
}
}
// Meta layer which adds itself in its list of component layers
TEST(MetaLayers, MetaLayerNameInComponentLayers) {
FrameworkEnvironment env;
env.add_icd(TestICDDetails(TEST_ICD_PATH_VERSION_2_EXPORT_ICD_GPDPA));
const char* meta_layer_name = "VK_LAYER_MetaTestLayer";
const char* regular_layer_name = "VK_LAYER_TestLayer";
env.add_implicit_layer(ManifestLayer{}.set_file_format_version({1, 1, 2}).add_layer(
ManifestLayer::LayerDescription{}
.set_name(meta_layer_name)
.add_component_layers({meta_layer_name, regular_layer_name})
.set_disable_environment("NotGonnaWork")
.add_instance_extension({"NeverGonnaGiveYouUp"})
.add_device_extension({"NeverGonnaLetYouDown"})),
"meta_test_layer.json");
env.add_explicit_layer(
ManifestLayer{}.add_layer(
ManifestLayer::LayerDescription{}.set_name(regular_layer_name).set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)),
"regular_test_layer.json");
// should find 1, the 'regular' layer
auto layer_props = env.GetLayerProperties(1);
EXPECT_TRUE(string_eq(layer_props.at(0).layerName, regular_layer_name));
auto extensions = env.GetInstanceExtensions(4);
EXPECT_TRUE(string_eq(extensions.at(0).extensionName, VK_EXT_DEBUG_REPORT_EXTENSION_NAME));
EXPECT_TRUE(string_eq(extensions.at(1).extensionName, VK_EXT_DEBUG_UTILS_EXTENSION_NAME));
EXPECT_TRUE(string_eq(extensions.at(2).extensionName, VK_KHR_PORTABILITY_ENUMERATION_EXTENSION_NAME));
EXPECT_TRUE(string_eq(extensions.at(3).extensionName, VK_LUNARG_DIRECT_DRIVER_LOADING_EXTENSION_NAME));
InstWrapper inst{env.vulkan_functions};
inst.create_info.add_layer(meta_layer_name);
FillDebugUtilsCreateDetails(inst.create_info, env.debug_log);
inst.CheckCreate(VK_ERROR_LAYER_NOT_PRESENT);
ASSERT_TRUE(env.debug_log.find(std::string("verify_meta_layer_component_layers: Meta-layer ") + meta_layer_name +
" lists itself in its component layer " + "list at index 0. Skipping this layer."));
}
// Meta layer which adds another meta layer as a component layer
TEST(MetaLayers, MetaLayerWhichAddsMetaLayer) {
FrameworkEnvironment env;
env.add_icd(TestICDDetails(TEST_ICD_PATH_VERSION_2_EXPORT_ICD_GPDPA));
const char* meta_layer_name = "VK_LAYER_MetaTestLayer";
const char* meta_meta_layer_name = "VK_LAYER_MetaMetaTestLayer";
const char* regular_layer_name = "VK_LAYER_TestLayer";
env.add_explicit_layer(
ManifestLayer{}.add_layer(
ManifestLayer::LayerDescription{}.set_name(regular_layer_name).set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)),
"regular_test_layer.json");
env.add_explicit_layer(
ManifestLayer{}.set_file_format_version({1, 1, 2}).add_layer(
ManifestLayer::LayerDescription{}.set_name(meta_layer_name).add_component_layers({regular_layer_name})),
"meta_test_layer.json");
env.add_explicit_layer(ManifestLayer{}.set_file_format_version({1, 1, 2}).add_layer(
ManifestLayer::LayerDescription{}
.set_name(meta_meta_layer_name)
.add_component_layers({meta_layer_name, regular_layer_name})),
"meta_meta_test_layer.json");
auto layer_props = env.GetLayerProperties(3);
EXPECT_TRUE(check_permutation({regular_layer_name, meta_layer_name, meta_meta_layer_name}, layer_props));
auto extensions = env.GetInstanceExtensions(4);
EXPECT_TRUE(string_eq(extensions.at(0).extensionName, VK_EXT_DEBUG_REPORT_EXTENSION_NAME));
EXPECT_TRUE(string_eq(extensions.at(1).extensionName, VK_EXT_DEBUG_UTILS_EXTENSION_NAME));
EXPECT_TRUE(string_eq(extensions.at(2).extensionName, VK_KHR_PORTABILITY_ENUMERATION_EXTENSION_NAME));
EXPECT_TRUE(string_eq(extensions.at(3).extensionName, VK_LUNARG_DIRECT_DRIVER_LOADING_EXTENSION_NAME));
InstWrapper inst{env.vulkan_functions};
inst.create_info.add_layer(meta_layer_name);
FillDebugUtilsCreateDetails(inst.create_info, env.debug_log);
inst.CheckCreate();
ASSERT_TRUE(env.debug_log.find(std::string("verify_meta_layer_component_layers: Adding meta-layer ") + meta_meta_layer_name +
" which also contains meta-layer " + meta_layer_name));
}
TEST(MetaLayers, InstanceExtensionInComponentLayer) {
FrameworkEnvironment env;
env.add_icd(TestICDDetails(TEST_ICD_PATH_VERSION_2_EXPORT_ICD_GPDPA)).add_physical_device({});
const char* meta_layer_name = "VK_LAYER_MetaTestLayer";
const char* regular_layer_name = "VK_LAYER_TestLayer";
const char* instance_ext_name = "VK_EXT_headless_surface";
env.add_explicit_layer(ManifestLayer{}.add_layer(ManifestLayer::LayerDescription{}
.set_name(regular_layer_name)
.set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)
.add_instance_extension({instance_ext_name})),
"regular_test_layer.json");
env.add_explicit_layer(
ManifestLayer{}.set_file_format_version({1, 1, 2}).add_layer(
ManifestLayer::LayerDescription{}.set_name(meta_layer_name).add_component_layers({regular_layer_name})),
"meta_test_layer.json");
auto extensions = env.GetInstanceExtensions(1, meta_layer_name);
EXPECT_TRUE(string_eq(extensions[0].extensionName, instance_ext_name));
}
TEST(MetaLayers, DeviceExtensionInComponentLayer) {
FrameworkEnvironment env;
env.add_icd(TestICDDetails(TEST_ICD_PATH_VERSION_2_EXPORT_ICD_GPDPA)).add_physical_device({});
const char* meta_layer_name = "VK_LAYER_MetaTestLayer";
const char* regular_layer_name = "VK_LAYER_TestLayer";
const char* device_ext_name = "VK_EXT_fake_dev_ext";
env.add_explicit_layer(ManifestLayer{}.add_layer(ManifestLayer::LayerDescription{}
.set_name(regular_layer_name)
.set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)
.add_device_extension({device_ext_name})),
"regular_test_layer.json");
env.add_explicit_layer(
ManifestLayer{}.set_file_format_version({1, 1, 2}).add_layer(
ManifestLayer::LayerDescription{}.set_name(meta_layer_name).add_component_layers({regular_layer_name})),
"meta_test_layer.json");
ASSERT_NO_FATAL_FAILURE(env.GetInstanceExtensions(0, meta_layer_name));
{ // layer is not enabled
InstWrapper inst{env.vulkan_functions};
FillDebugUtilsCreateDetails(inst.create_info, env.debug_log);
inst.CheckCreate();
ASSERT_TRUE(env.debug_log.find(std::string("Meta-layer ") + meta_layer_name + " component layer " + regular_layer_name +
" adding device extension " + device_ext_name));
auto extensions = inst.EnumerateLayerDeviceExtensions(inst.GetPhysDev(), meta_layer_name, 1);
EXPECT_TRUE(string_eq(extensions.at(0).extensionName, device_ext_name));
}
{ // layer is enabled
InstWrapper inst{env.vulkan_functions};
inst.create_info.add_layer(meta_layer_name);
FillDebugUtilsCreateDetails(inst.create_info, env.debug_log);
inst.CheckCreate();
ASSERT_TRUE(env.debug_log.find(std::string("Meta-layer ") + meta_layer_name + " component layer " + regular_layer_name +
" adding device extension " + device_ext_name));
auto extensions = inst.EnumerateLayerDeviceExtensions(inst.GetPhysDev(), meta_layer_name, 1);
EXPECT_TRUE(string_eq(extensions.at(0).extensionName, device_ext_name));
}
}
// Override meta layer missing disable environment variable still enables the layer
TEST(OverrideMetaLayer, InvalidDisableEnvironment) {
FrameworkEnvironment env;
env.add_icd(TestICDDetails(TEST_ICD_PATH_VERSION_2_EXPORT_ICD_GPDPA)).add_physical_device({});
const char* regular_layer_name = "VK_LAYER_TestLayer";
env.add_explicit_layer(ManifestLayer{}.add_layer(ManifestLayer::LayerDescription{}
.set_name(regular_layer_name)
.set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)
.set_api_version(VK_MAKE_API_VERSION(0, 1, 1, 0))
.add_device_extension({"NeverGonnaLetYouDown"})),
"regular_test_layer.json");
env.add_implicit_layer(
ManifestLayer{}.set_file_format_version({1, 1, 2}).add_layer(ManifestLayer::LayerDescription{}
.set_name(lunarg_meta_layer_name)
.set_api_version(VK_MAKE_API_VERSION(0, 1, 1, 0))
.add_component_layers({regular_layer_name})),
"meta_test_layer.json");
auto layer_props = env.GetLayerProperties(1);
EXPECT_TRUE(string_eq(layer_props[0].layerName, regular_layer_name));
InstWrapper inst{env.vulkan_functions};
inst.CheckCreate();
}
// Override meta layer whose version is less than the api version of the instance
TEST(OverrideMetaLayer, OlderVersionThanInstance) {
FrameworkEnvironment env;
env.add_icd(TestICDDetails(TEST_ICD_PATH_VERSION_2_EXPORT_ICD_GPDPA)).add_physical_device({});
const char* regular_layer_name = "VK_LAYER_TestLayer";
env.add_explicit_layer(ManifestLayer{}.add_layer(ManifestLayer::LayerDescription{}
.set_name(regular_layer_name)
.set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)
.set_api_version(VK_MAKE_API_VERSION(0, 1, 1, 0))
.add_device_extension({"NeverGonnaLetYouDown"})),
"regular_test_layer.json");
env.add_implicit_layer(
ManifestLayer{}.set_file_format_version({1, 1, 2}).add_layer(ManifestLayer::LayerDescription{}
.set_name(lunarg_meta_layer_name)
.set_api_version(VK_MAKE_API_VERSION(0, 1, 1, 0))
.set_disable_environment("DisableMeIfYouCan")
.add_component_layers({regular_layer_name})),
"meta_test_layer.json");
{ // global functions
auto layer_props = env.GetLayerProperties(2);
EXPECT_TRUE(check_permutation({regular_layer_name, lunarg_meta_layer_name}, layer_props));
}
{ // 1.1 instance
InstWrapper inst{env.vulkan_functions};
inst.create_info.api_version = VK_API_VERSION_1_1;
inst.CheckCreate();
auto layer_props = inst.GetActiveLayers(inst.GetPhysDev(), 2);
ASSERT_TRUE(string_eq(layer_props[0].layerName, regular_layer_name));
ASSERT_TRUE(string_eq(layer_props[1].layerName, lunarg_meta_layer_name));
}
{ // 1.3 instance
InstWrapper inst{env.vulkan_functions};
inst.create_info.api_version = VK_API_VERSION_1_3;
inst.CheckCreate();
auto layer_props = inst.GetActiveLayers(inst.GetPhysDev(), 2);
ASSERT_TRUE(string_eq(layer_props[0].layerName, regular_layer_name));
ASSERT_TRUE(string_eq(layer_props[1].layerName, lunarg_meta_layer_name));
}
}
TEST(OverrideMetaLayer, OlderMetaLayerWithNewerInstanceVersion) {
FrameworkEnvironment env;
env.add_icd(TestICDDetails(TEST_ICD_PATH_VERSION_2_EXPORT_ICD_GPDPA)).add_physical_device({});
const char* regular_layer_name = "VK_LAYER_TestLayer";
env.add_explicit_layer(
ManifestLayer{}.set_file_format_version({1, 2, 0}).add_layer(ManifestLayer::LayerDescription{}
.set_name(regular_layer_name)
.set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)
.set_api_version(VK_MAKE_API_VERSION(0, 1, 1, 0))),
"regular_test_layer.json");
env.add_implicit_layer(
ManifestLayer{}.set_file_format_version({1, 2, 0}).add_layer(ManifestLayer::LayerDescription{}
.set_name(lunarg_meta_layer_name)
.set_api_version(VK_MAKE_API_VERSION(0, 1, 1, 0))
.add_component_layers({regular_layer_name})
.set_disable_environment("DisableMeIfYouCan")),
"meta_test_layer.json");
{ // global functions
auto layer_props = env.GetLayerProperties(2);
EXPECT_TRUE(check_permutation({regular_layer_name, lunarg_meta_layer_name}, layer_props));
}
{
// 1.1 instance
InstWrapper inst{env.vulkan_functions};
inst.create_info.set_api_version(1, 1, 0);
inst.CheckCreate();
auto layer_props = inst.GetActiveLayers(inst.GetPhysDev(), 2);
ASSERT_TRUE(string_eq(layer_props[0].layerName, regular_layer_name));
ASSERT_TRUE(string_eq(layer_props[1].layerName, lunarg_meta_layer_name));
}
{
// 1.3 instance
InstWrapper inst{env.vulkan_functions};
inst.create_info.set_api_version(1, 3, 0);
inst.CheckCreate();
auto layer_props = inst.GetActiveLayers(inst.GetPhysDev(), 2);
ASSERT_TRUE(string_eq(layer_props[0].layerName, regular_layer_name));
ASSERT_TRUE(string_eq(layer_props[1].layerName, lunarg_meta_layer_name));
}
}
TEST(OverrideMetaLayer, NewerComponentLayerInMetaLayer) {
FrameworkEnvironment env;
env.add_icd(TestICDDetails(TEST_ICD_PATH_VERSION_2_EXPORT_ICD_GPDPA)).add_physical_device({});
const char* regular_layer_name = "VK_LAYER_TestLayer";
env.add_explicit_layer(
ManifestLayer{}.set_file_format_version({1, 2, 0}).add_layer(ManifestLayer::LayerDescription{}
.set_name(regular_layer_name)
.set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)
.set_api_version(VK_API_VERSION_1_2)),
"regular_test_layer.json");
env.add_implicit_layer(
ManifestLayer{}.set_file_format_version({1, 2, 0}).add_layer(ManifestLayer::LayerDescription{}
.set_name(lunarg_meta_layer_name)
.set_api_version(VK_MAKE_API_VERSION(0, 1, 1, 0))
.add_component_layers({regular_layer_name})
.set_disable_environment("DisableMeIfYouCan")),
"meta_test_layer.json");
{ // global functions
auto layer_props = env.GetLayerProperties(2);
// Expect the explicit layer to still be found
EXPECT_TRUE(check_permutation({regular_layer_name, lunarg_meta_layer_name}, layer_props));
}
{
// 1.1 instance
InstWrapper inst{env.vulkan_functions};
FillDebugUtilsCreateDetails(inst.create_info, env.debug_log);
inst.create_info.set_api_version(1, 1, 0);
inst.CheckCreate();
// Newer component is allowed now
EXPECT_TRUE(env.debug_log.find(std::string("Insert instance layer \"") + regular_layer_name));
auto layer_props = inst.GetActiveLayers(inst.GetPhysDev(), 2);
EXPECT_TRUE(check_permutation({regular_layer_name, lunarg_meta_layer_name}, layer_props));
}
env.debug_log.clear();
{
// 1.3 instance
InstWrapper inst{env.vulkan_functions};
FillDebugUtilsCreateDetails(inst.create_info, env.debug_log);
inst.create_info.set_api_version(1, 3, 0);
inst.CheckCreate();
// Newer component is allowed now
EXPECT_TRUE(env.debug_log.find(std::string("Insert instance layer \"") + regular_layer_name));
auto layer_props = inst.GetActiveLayers(inst.GetPhysDev(), 2);
EXPECT_TRUE(check_permutation({regular_layer_name, lunarg_meta_layer_name}, layer_props));
}
}
TEST(OverrideMetaLayer, OlderComponentLayerInMetaLayer) {
FrameworkEnvironment env;
env.add_icd(TestICDDetails(TEST_ICD_PATH_VERSION_2_EXPORT_ICD_GPDPA)).add_physical_device({});
const char* regular_layer_name = "VK_LAYER_TestLayer";
env.add_explicit_layer(
ManifestLayer{}.set_file_format_version({1, 2, 0}).add_layer(ManifestLayer::LayerDescription{}
.set_name(regular_layer_name)
.set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)
.set_api_version(VK_MAKE_API_VERSION(0, 1, 0, 0))),
"regular_test_layer.json");
env.add_implicit_layer(
ManifestLayer{}.set_file_format_version({1, 2, 0}).add_layer(ManifestLayer::LayerDescription{}
.set_name(lunarg_meta_layer_name)
.set_api_version(VK_MAKE_API_VERSION(0, 1, 1, 0))
.add_component_layers({regular_layer_name})
.set_disable_environment("DisableMeIfYouCan")),
"meta_test_layer.json");
{ // global functions
auto layer_props = env.GetLayerProperties(1);
EXPECT_TRUE(string_eq(layer_props[0].layerName, regular_layer_name));
}
{
// 1.1 instance
InstWrapper inst{env.vulkan_functions};
FillDebugUtilsCreateDetails(inst.create_info, env.debug_log);
inst.create_info.set_api_version(1, 1, 0);
inst.CheckCreate();
EXPECT_TRUE(
env.debug_log.find("verify_meta_layer_component_layers: Meta-layer uses API version 1.1, but component layer 0 has API "
"version 1.0 that is lower. Skipping this layer."));
env.debug_log.clear();
ASSERT_NO_FATAL_FAILURE(inst.GetActiveLayers(inst.GetPhysDev(), 0));
}
{
// 1.2 instance
InstWrapper inst{env.vulkan_functions};
FillDebugUtilsCreateDetails(inst.create_info, env.debug_log);
inst.create_info.set_api_version(1, 2, 0);
inst.CheckCreate();
ASSERT_TRUE(
env.debug_log.find("verify_meta_layer_component_layers: Meta-layer uses API version 1.1, but component layer 0 has API "
"version 1.0 that is lower. Skipping this layer."));
env.debug_log.clear();
ASSERT_NO_FATAL_FAILURE(inst.GetActiveLayers(inst.GetPhysDev(), 0));
}
}
TEST(OverrideMetaLayer, ApplicationEnabledLayerInBlacklist) {
FrameworkEnvironment env;
env.add_icd(TestICDDetails(TEST_ICD_PATH_VERSION_2_EXPORT_ICD_GPDPA)).add_physical_device({});
const char* automatic_regular_layer_name = "VK_LAYER_TestLayer_1";
const char* manual_regular_layer_name = "VK_LAYER_TestLayer_2";
env.add_explicit_layer(ManifestLayer{}.add_layer(ManifestLayer::LayerDescription{}
.set_name(automatic_regular_layer_name)
.set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)
.set_api_version(VK_MAKE_API_VERSION(0, 1, 1, 0))),
"regular_test_layer_1.json");
env.add_explicit_layer(ManifestLayer{}.add_layer(ManifestLayer::LayerDescription{}
.set_name(manual_regular_layer_name)
.set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)
.set_api_version(VK_MAKE_API_VERSION(0, 1, 1, 0))),
"regular_test_layer_2.json");
env.add_implicit_layer(
ManifestLayer{}.set_file_format_version({1, 2, 0}).add_layer(ManifestLayer::LayerDescription{}
.set_name(lunarg_meta_layer_name)
.set_api_version(VK_MAKE_API_VERSION(0, 1, 1, 0))
.add_component_layer(automatic_regular_layer_name)
.add_blacklisted_layer(manual_regular_layer_name)
.set_disable_environment("DisableMeIfYouCan")),
"meta_test_layer.json");
{ // Check that enumerating the layers returns only the non-blacklisted layers + override layer
auto layer_props = env.GetLayerProperties(2);
ASSERT_TRUE(check_permutation({automatic_regular_layer_name, lunarg_meta_layer_name}, layer_props));
}
{
// enable the layer in the blacklist
InstWrapper inst{env.vulkan_functions};
FillDebugUtilsCreateDetails(inst.create_info, env.debug_log);
inst.create_info.add_layer(manual_regular_layer_name);
inst.CheckCreate(VK_ERROR_LAYER_NOT_PRESENT);
ASSERT_TRUE(env.debug_log.find(std::string("loader_remove_layers_in_blacklist: Override layer is active and layer ") +
manual_regular_layer_name +
" is in the blacklist inside of it. Removing that layer from current layer list."));
env.debug_log.clear();
}
{ // dont enable the layer in the blacklist
InstWrapper inst{env.vulkan_functions};
FillDebugUtilsCreateDetails(inst.create_info, env.debug_log);
inst.CheckCreate();
ASSERT_TRUE(env.debug_log.find(std::string("loader_remove_layers_in_blacklist: Override layer is active and layer ") +
manual_regular_layer_name +
" is in the blacklist inside of it. Removing that layer from current layer list."));
env.debug_log.clear();
auto layer_props = inst.GetActiveLayers(inst.GetPhysDev(), 2);
ASSERT_TRUE(check_permutation({automatic_regular_layer_name, lunarg_meta_layer_name}, layer_props));
}
}
TEST(OverrideMetaLayer, BasicOverridePaths) {
FrameworkEnvironment env;
env.add_icd(TestICDDetails(TEST_ICD_PATH_VERSION_2_EXPORT_ICD_GPDPA)).add_physical_device({});
fs::FolderManager override_layer_folder{FRAMEWORK_BUILD_DIRECTORY, "override_layer_folder"};
const char* regular_layer_name = "VK_LAYER_TestLayer_1";
override_layer_folder.write_manifest("regular_test_layer.json",
ManifestLayer{}
.add_layer(ManifestLayer::LayerDescription{}
.set_name(regular_layer_name)
.set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)
.set_api_version(VK_MAKE_API_VERSION(0, 1, 1, 0)))
.get_manifest_str());
env.add_implicit_layer(
ManifestLayer{}.set_file_format_version({1, 2, 0}).add_layer(ManifestLayer::LayerDescription{}
.set_name(lunarg_meta_layer_name)
.set_api_version(VK_MAKE_API_VERSION(0, 1, 1, 0))
.add_component_layer(regular_layer_name)
.set_disable_environment("DisableMeIfYouCan")
.add_override_path(override_layer_folder.location())),
"meta_test_layer.json");
InstWrapper inst{env.vulkan_functions};
inst.create_info.set_api_version(1, 1, 0);
FillDebugUtilsCreateDetails(inst.create_info, env.debug_log);
inst.CheckCreate();
ASSERT_TRUE(env.debug_log.find(std::string("Insert instance layer \"") + regular_layer_name));
env.layers.clear();
}
TEST(OverrideMetaLayer, BasicOverridePathsIgnoreOtherLayers) {
FrameworkEnvironment env;
env.add_icd(TestICDDetails(TEST_ICD_PATH_VERSION_2_EXPORT_ICD_GPDPA)).add_physical_device({});
fs::FolderManager override_layer_folder{FRAMEWORK_BUILD_DIRECTORY, "override_layer_folder"};
const char* regular_layer_name = "VK_LAYER_TestLayer";
env.add_explicit_layer(
ManifestLayer{}.set_file_format_version({1, 2, 0}).add_layer(ManifestLayer::LayerDescription{}
.set_name(regular_layer_name)
.set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)
.set_api_version(VK_MAKE_API_VERSION(0, 1, 0, 0))),
"regular_test_layer.json");
const char* special_layer_name = "VK_LAYER_TestLayer_1";
override_layer_folder.write_manifest("regular_test_layer.json",
ManifestLayer{}
.add_layer(ManifestLayer::LayerDescription{}
.set_name(special_layer_name)
.set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)
.set_api_version(VK_MAKE_API_VERSION(0, 1, 1, 0)))
.get_manifest_str());
env.add_implicit_layer(
ManifestLayer{}.set_file_format_version({1, 2, 0}).add_layer(ManifestLayer::LayerDescription{}
.set_name(lunarg_meta_layer_name)
.set_api_version(VK_MAKE_API_VERSION(0, 1, 1, 0))
.add_component_layer(special_layer_name)
.set_disable_environment("DisableMeIfYouCan")
.add_override_path(override_layer_folder.location())),
"meta_test_layer.json");
InstWrapper inst{env.vulkan_functions};
inst.create_info.set_api_version(1, 1, 0);
inst.create_info.add_layer(regular_layer_name);
FillDebugUtilsCreateDetails(inst.create_info, env.debug_log);
inst.CheckCreate(VK_ERROR_LAYER_NOT_PRESENT);
ASSERT_FALSE(env.debug_log.find(std::string("Insert instance layer \"") + regular_layer_name));
env.layers.clear();
}
TEST(OverrideMetaLayer, OverridePathsInteractionWithVK_LAYER_PATH) {
FrameworkEnvironment env;
env.add_icd(TestICDDetails(TEST_ICD_PATH_VERSION_2_EXPORT_ICD_GPDPA)).add_physical_device({});
// add explicit layer to VK_LAYER_PATH folder
const char* env_var_layer_name = "VK_LAYER_env_var_set_path";
env.add_explicit_layer(TestLayerDetails{
ManifestLayer{}.set_file_format_version({1, 2, 0}).add_layer(ManifestLayer::LayerDescription{}
.set_name(env_var_layer_name)
.set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)
.set_api_version(VK_MAKE_API_VERSION(0, 1, 0, 0))),
"regular_test_layer.json"}
.set_discovery_type(ManifestDiscoveryType::env_var));
// add layer to regular explicit layer folder
const char* regular_layer_name = "VK_LAYER_regular_layer_path";
env.add_explicit_layer(TestLayerDetails{ManifestLayer{}.add_layer(ManifestLayer::LayerDescription{}
.set_name(regular_layer_name)
.set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)
.set_api_version(VK_MAKE_API_VERSION(0, 1, 1, 0))),
"regular_test_layer.json"}
.set_discovery_type(ManifestDiscoveryType::override_folder));
env.add_implicit_layer(ManifestLayer{}.set_file_format_version({1, 2, 0}).add_layer(
ManifestLayer::LayerDescription{}
.set_name(lunarg_meta_layer_name)
.set_api_version(VK_MAKE_API_VERSION(0, 1, 1, 0))
.add_component_layer(regular_layer_name)
.set_disable_environment("DisableMeIfYouCan")
.add_override_path(env.get_folder(ManifestLocation::override_layer).location())),
"meta_test_layer.json");
auto meta_layer_path = env.get_folder(ManifestLocation::override_layer).location();
InstWrapper inst{env.vulkan_functions};
inst.create_info.set_api_version(1, 1, 0);
inst.create_info.add_layer(env_var_layer_name);
FillDebugUtilsCreateDetails(inst.create_info, env.debug_log);
inst.CheckCreate(VK_ERROR_LAYER_NOT_PRESENT);
ASSERT_FALSE(env.debug_log.find(std::string("Insert instance layer \"") + env_var_layer_name));
ASSERT_TRUE(env.debug_log.find(
std::string("Ignoring VK_LAYER_PATH. The Override layer is active and has override paths set, which takes priority. "
"VK_LAYER_PATH is set to ") +
env.env_var_vk_layer_paths.value()));
ASSERT_TRUE(env.debug_log.find("Override layer has override paths set to " + meta_layer_path.string()));
env.layers.clear();
}
// Make sure that implicit layers not in the override paths aren't found by mistake
TEST(OverrideMetaLayer, OverridePathsEnableImplicitLayerInDefaultPaths) {
FrameworkEnvironment env;
env.add_icd(TestICDDetails(TEST_ICD_PATH_VERSION_2_EXPORT_ICD_GPDPA)).add_physical_device({});
fs::FolderManager override_layer_folder{FRAMEWORK_BUILD_DIRECTORY, "override_layer_folder"};
const char* implicit_layer_name = "VK_LAYER_ImplicitLayer";
env.add_implicit_layer(
ManifestLayer{}.set_file_format_version({1, 2, 0}).add_layer(ManifestLayer::LayerDescription{}
.set_name(implicit_layer_name)
.set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)
.set_api_version(VK_MAKE_API_VERSION(0, 1, 0, 0))),
"implicit_test_layer.json");
const char* regular_layer_name = "VK_LAYER_TestLayer_1";
override_layer_folder.write_manifest("regular_test_layer.json",
ManifestLayer{}
.add_layer(ManifestLayer::LayerDescription{}
.set_name(regular_layer_name)
.set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)
.set_api_version(VK_MAKE_API_VERSION(0, 1, 1, 0)))
.get_manifest_str());
env.add_implicit_layer(ManifestLayer{}.set_file_format_version({1, 2, 0}).add_layer(
ManifestLayer::LayerDescription{}
.set_name(lunarg_meta_layer_name)
.set_api_version(VK_MAKE_API_VERSION(0, 1, 1, 0))
.add_component_layers({regular_layer_name, implicit_layer_name})
.set_disable_environment("DisableMeIfYouCan")
.add_override_path(override_layer_folder.location())),
"meta_test_layer.json");
InstWrapper inst{env.vulkan_functions};
FillDebugUtilsCreateDetails(inst.create_info, env.debug_log);
inst.create_info.set_api_version(1, 1, 0);
inst.CheckCreate();
ASSERT_FALSE(env.debug_log.find(std::string("Insert instance layer \"") + implicit_layer_name));
ASSERT_TRUE(
env.debug_log.find("Removing meta-layer VK_LAYER_LUNARG_override from instance layer list since it appears invalid."));
env.layers.clear();
}
TEST(OverrideMetaLayer, ManifestFileFormatVersionTooOld) {
FrameworkEnvironment env;
env.add_icd(TestICDDetails(TEST_ICD_PATH_VERSION_2_EXPORT_ICD_GPDPA)).add_physical_device({});
fs::FolderManager override_layer_folder{FRAMEWORK_BUILD_DIRECTORY, "override_layer_folder"};
const char* regular_layer_name = "VK_LAYER_TestLayer_1";
override_layer_folder.write_manifest("regular_test_layer.json",
ManifestLayer{}
.add_layer(ManifestLayer::LayerDescription{}
.set_name(regular_layer_name)
.set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)
.set_api_version(VK_MAKE_API_VERSION(0, 1, 1, 0)))
.get_manifest_str());
env.add_implicit_layer(
ManifestLayer{}.set_file_format_version({1, 0, 0}).add_layer(ManifestLayer::LayerDescription{}
.set_name(lunarg_meta_layer_name)
.set_api_version(VK_MAKE_API_VERSION(0, 1, 1, 0))
.add_component_layer(regular_layer_name)
.set_disable_environment("DisableMeIfYouCan")
.add_override_path(override_layer_folder.location())),
"meta_test_layer.json");
InstWrapper inst{env.vulkan_functions};
inst.create_info.set_api_version(1, 1, 0);
FillDebugUtilsCreateDetails(inst.create_info, env.debug_log);
inst.CheckCreate();
ASSERT_TRUE(env.debug_log.find(std::string("Insert instance layer \"") + regular_layer_name));
ASSERT_TRUE(env.debug_log.find("Indicating meta-layer-specific override paths, but using older JSON file version."));
env.layers.clear();
}
// app_key contains test executable name, should activate the override layer
TEST(OverrideMetaLayer, AppKeysDoesContainCurrentApplication) {
FrameworkEnvironment env;
env.add_icd(TestICDDetails(TEST_ICD_PATH_VERSION_2_EXPORT_ICD_GPDPA)).add_physical_device({});
const char* regular_layer_name = "VK_LAYER_TestLayer";
env.add_explicit_layer(
ManifestLayer{}.set_file_format_version({1, 2, 0}).add_layer(
ManifestLayer::LayerDescription{}.set_name(regular_layer_name).set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)),
"regular_test_layer.json");
std::string cur_path = test_platform_executable_path();
env.add_implicit_layer(
ManifestLayer{}.set_file_format_version({1, 2, 0}).add_layer(ManifestLayer::LayerDescription{}
.set_name(lunarg_meta_layer_name)
.add_component_layers({regular_layer_name})
.set_disable_environment("DisableMeIfYouCan")
.add_app_key(cur_path)),
"meta_test_layer.json");
{ // global functions
auto layer_props = env.GetLayerProperties(2);
EXPECT_TRUE(check_permutation({regular_layer_name, lunarg_meta_layer_name}, layer_props));
}
{
// instance
InstWrapper inst{env.vulkan_functions};
inst.CheckCreate();
auto layer_props = inst.GetActiveLayers(inst.GetPhysDev(), 2);
EXPECT_TRUE(check_permutation({regular_layer_name, lunarg_meta_layer_name}, layer_props));
}
}
// app_key contains random strings, should not activate the override layer
TEST(OverrideMetaLayer, AppKeysDoesNotContainCurrentApplication) {
FrameworkEnvironment env;
env.add_icd(TestICDDetails(TEST_ICD_PATH_VERSION_2_EXPORT_ICD_GPDPA)).add_physical_device({});
const char* regular_layer_name = "VK_LAYER_TestLayer";
env.add_explicit_layer(
ManifestLayer{}.set_file_format_version({1, 2, 0}).add_layer(
ManifestLayer::LayerDescription{}.set_name(regular_layer_name).set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)),
"regular_test_layer.json");
env.add_implicit_layer(ManifestLayer{}.set_file_format_version({1, 2, 0}).add_layer(
ManifestLayer::LayerDescription{}
.set_name(lunarg_meta_layer_name)
.add_component_layers({regular_layer_name})
.set_disable_environment("DisableMeIfYouCan")
.add_app_keys({"/Hello", "Hi", "./../Uh-oh", "C:/Windows/Only"})),
"meta_test_layer.json");
{ // global functions
auto layer_props = env.GetLayerProperties(1);
EXPECT_TRUE(string_eq(layer_props[0].layerName, regular_layer_name));
}
{
// instance
InstWrapper inst{env.vulkan_functions};
inst.CheckCreate();
ASSERT_NO_FATAL_FAILURE(inst.GetActiveLayers(inst.GetPhysDev(), 0));
}
}
TEST(OverrideMetaLayer, RunningWithElevatedPrivilegesFromSecureLocation) {
FrameworkEnvironment env;
env.add_icd(TestICDDetails(TEST_ICD_PATH_VERSION_2_EXPORT_ICD_GPDPA)).add_physical_device({});
fs::FolderManager override_layer_folder{FRAMEWORK_BUILD_DIRECTORY, "override_layer_folder"};
const char* regular_layer_name = "VK_LAYER_TestLayer_1";
override_layer_folder.write_manifest("regular_test_layer.json",
ManifestLayer{}
.add_layer(ManifestLayer::LayerDescription{}
.set_name(regular_layer_name)
.set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)
.set_api_version(VK_MAKE_API_VERSION(0, 1, 1, 0)))
.get_manifest_str());
auto override_folder_location = override_layer_folder.location().string();
env.add_implicit_layer(TestLayerDetails{
ManifestLayer{}.set_file_format_version({1, 2, 0}).add_layer(ManifestLayer::LayerDescription{}
.set_name(lunarg_meta_layer_name)
.set_api_version(VK_MAKE_API_VERSION(0, 1, 1, 0))
.add_component_layer(regular_layer_name)
.set_disable_environment("DisableMeIfYouCan")
.add_override_path(override_layer_folder.location())),
"meta_test_layer.json"});
{ // try with no elevated privileges
auto layer_props = env.GetLayerProperties(2);
EXPECT_TRUE(check_permutation({regular_layer_name, lunarg_meta_layer_name}, layer_props));
InstWrapper inst{env.vulkan_functions};
inst.create_info.set_api_version(1, 1, 0);
FillDebugUtilsCreateDetails(inst.create_info, env.debug_log);
inst.CheckCreate();
ASSERT_TRUE(env.debug_log.find(std::string("Insert instance layer \"") + regular_layer_name));
auto active_layer_props = inst.GetActiveLayers(inst.GetPhysDev(), 2);
EXPECT_TRUE(check_permutation({regular_layer_name, lunarg_meta_layer_name}, layer_props));
env.debug_log.clear();
}
env.platform_shim->set_elevated_privilege(true);
{ // try with elevated privileges
auto layer_props = env.GetLayerProperties(2);
EXPECT_TRUE(check_permutation({regular_layer_name, lunarg_meta_layer_name}, layer_props));
InstWrapper inst{env.vulkan_functions};
inst.create_info.set_api_version(1, 1, 0);
FillDebugUtilsCreateDetails(inst.create_info, env.debug_log);
inst.CheckCreate();
ASSERT_TRUE(env.debug_log.find(std::string("Insert instance layer \"") + regular_layer_name));
auto active_layer_props = inst.GetActiveLayers(inst.GetPhysDev(), 2);
EXPECT_TRUE(check_permutation({regular_layer_name, lunarg_meta_layer_name}, active_layer_props));
}
}
// Override layer should not be found and thus not loaded when running with elevated privileges
TEST(OverrideMetaLayer, RunningWithElevatedPrivilegesFromUnsecureLocation) {
FrameworkEnvironment env;
env.add_icd(TestICDDetails(TEST_ICD_PATH_VERSION_2_EXPORT_ICD_GPDPA)).add_physical_device({});
fs::FolderManager override_layer_folder{FRAMEWORK_BUILD_DIRECTORY, "override_layer_folder"};
const char* regular_layer_name = "VK_LAYER_TestLayer_1";
override_layer_folder.write_manifest("regular_test_layer.json",
ManifestLayer{}
.add_layer(ManifestLayer::LayerDescription{}
.set_name(regular_layer_name)
.set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)
.set_api_version(VK_MAKE_API_VERSION(0, 1, 1, 0)))
.get_manifest_str());
env.add_implicit_layer(TestLayerDetails{
ManifestLayer{}.set_file_format_version({1, 2, 0}).add_layer(ManifestLayer::LayerDescription{}
.set_name(lunarg_meta_layer_name)
.set_api_version(VK_MAKE_API_VERSION(0, 1, 1, 0))
.add_component_layer(regular_layer_name)
.set_disable_environment("DisableMeIfYouCan")
.add_override_path(override_layer_folder.location())),
"meta_test_layer.json"}
.set_discovery_type(ManifestDiscoveryType::unsecured_generic));
{ // try with no elevated privileges
auto layer_props = env.GetLayerProperties(2);
EXPECT_TRUE(check_permutation({regular_layer_name, lunarg_meta_layer_name}, layer_props));
InstWrapper inst{env.vulkan_functions};
inst.create_info.set_api_version(1, 1, 0);
FillDebugUtilsCreateDetails(inst.create_info, env.debug_log);
inst.CheckCreate();
ASSERT_TRUE(env.debug_log.find(std::string("Insert instance layer \"") + regular_layer_name));
env.debug_log.clear();
auto active_layer_props = inst.GetActiveLayers(inst.GetPhysDev(), 2);
EXPECT_TRUE(check_permutation({regular_layer_name, lunarg_meta_layer_name}, active_layer_props));
}
env.platform_shim->set_elevated_privilege(true);
{ // try with no elevated privileges
ASSERT_NO_FATAL_FAILURE(env.GetLayerProperties(0));
InstWrapper inst{env.vulkan_functions};
inst.create_info.set_api_version(1, 1, 0);
FillDebugUtilsCreateDetails(inst.create_info, env.debug_log);
inst.CheckCreate();
ASSERT_FALSE(env.debug_log.find(std::string("Insert instance layer \"") + regular_layer_name));
ASSERT_NO_FATAL_FAILURE(inst.GetActiveLayers(inst.GetPhysDev(), 0));
}
}
// Makes sure explicit layers can't override pre-instance functions even if enabled by the override layer
TEST(ExplicitLayers, OverridePreInstanceFunctions) {
FrameworkEnvironment env;
env.add_icd(TestICDDetails(TEST_ICD_PATH_VERSION_2_EXPORT_ICD_GPDPA)).add_physical_device({});
const char* explicit_layer_name = "VK_LAYER_enabled_by_override";
const char* disable_env_var = "DISABLE_ME";
env.add_explicit_layer(
ManifestLayer{}.set_file_format_version({1, 1, 2}).add_layer(
ManifestLayer::LayerDescription{}
.set_name(explicit_layer_name)
.set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)
.add_pre_instance_function(ManifestLayer::LayerDescription::FunctionOverride{}
.set_vk_func("vkEnumerateInstanceLayerProperties")
.set_override_name("test_preinst_vkEnumerateInstanceLayerProperties"))
.add_pre_instance_function(ManifestLayer::LayerDescription::FunctionOverride{}
.set_vk_func("vkEnumerateInstanceExtensionProperties")
.set_override_name("test_preinst_vkEnumerateInstanceExtensionProperties"))
.add_pre_instance_function(ManifestLayer::LayerDescription::FunctionOverride{}
.set_vk_func("vkEnumerateInstanceVersion")
.set_override_name("test_preinst_vkEnumerateInstanceVersion"))),
"explicit_test_layer.json");
auto& layer = env.get_test_layer(0);
layer.set_reported_layer_props(34);
layer.set_reported_extension_props(22);
layer.set_reported_instance_version(VK_MAKE_API_VERSION(1, 0, 0, 1));
env.add_implicit_layer(
ManifestLayer{}.set_file_format_version({1, 1, 2}).add_layer(ManifestLayer::LayerDescription{}
.set_name(lunarg_meta_layer_name)
.add_component_layers({explicit_layer_name})
.set_disable_environment(disable_env_var)),
"override_meta_layer.json");
uint32_t count = 0;
ASSERT_EQ(VK_SUCCESS, env.vulkan_functions.vkEnumerateInstanceLayerProperties(&count, nullptr));
ASSERT_EQ(count, 2U);
count = 0;
ASSERT_EQ(VK_SUCCESS, env.vulkan_functions.vkEnumerateInstanceExtensionProperties(nullptr, &count, nullptr));
ASSERT_EQ(count, 4U);
uint32_t version = 0;
ASSERT_EQ(VK_SUCCESS, env.vulkan_functions.vkEnumerateInstanceVersion(&version));
ASSERT_EQ(version, VK_HEADER_VERSION_COMPLETE);
InstWrapper inst{env.vulkan_functions};
inst.CheckCreate();
auto layers = inst.GetActiveLayers(inst.GetPhysDev(), 2);
ASSERT_TRUE(string_eq(layers.at(0).layerName, explicit_layer_name));
ASSERT_TRUE(string_eq(layers.at(1).layerName, lunarg_meta_layer_name));
}
TEST(ExplicitLayers, LayerSettingsPreInstanceFunctions) {
FrameworkEnvironment env;
env.add_icd(TestICDDetails(TEST_ICD_PATH_VERSION_2_EXPORT_ICD_GPDPA)).add_physical_device({});
const char* explicit_layer_name = "VK_LAYER_enabled_by_override";
env.add_explicit_layer(
ManifestLayer{}.set_file_format_version({1, 1, 2}).add_layer(
ManifestLayer::LayerDescription{}
.set_name(explicit_layer_name)
.set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)
.add_pre_instance_function(ManifestLayer::LayerDescription::FunctionOverride{}
.set_vk_func("vkEnumerateInstanceLayerProperties")
.set_override_name("test_preinst_vkEnumerateInstanceLayerProperties"))
.add_pre_instance_function(ManifestLayer::LayerDescription::FunctionOverride{}
.set_vk_func("vkEnumerateInstanceExtensionProperties")
.set_override_name("test_preinst_vkEnumerateInstanceExtensionProperties"))
.add_pre_instance_function(ManifestLayer::LayerDescription::FunctionOverride{}
.set_vk_func("vkEnumerateInstanceVersion")
.set_override_name("test_preinst_vkEnumerateInstanceVersion"))),
"explicit_test_layer.json");
env.loader_settings.add_app_specific_setting(AppSpecificSettings{}.add_stderr_log_filter("all").add_layer_configuration(
LoaderSettingsLayerConfiguration{}
.set_name(explicit_layer_name)
.set_control("on")
.set_path(env.get_shimmed_layer_manifest_path(0))
.set_treat_as_implicit_manifest(false)));
env.update_loader_settings(env.loader_settings);
auto& layer = env.get_test_layer(0);
layer.set_reported_layer_props(34);
layer.set_reported_extension_props(22);
layer.set_reported_instance_version(VK_MAKE_API_VERSION(1, 0, 0, 1));
uint32_t count = 0;
ASSERT_EQ(VK_SUCCESS, env.vulkan_functions.vkEnumerateInstanceLayerProperties(&count, nullptr));
ASSERT_EQ(count, 1U);
count = 0;
ASSERT_EQ(VK_SUCCESS, env.vulkan_functions.vkEnumerateInstanceExtensionProperties(nullptr, &count, nullptr));
ASSERT_EQ(count, 4U);
uint32_t version = 0;
ASSERT_EQ(VK_SUCCESS, env.vulkan_functions.vkEnumerateInstanceVersion(&version));
ASSERT_EQ(version, VK_HEADER_VERSION_COMPLETE);
InstWrapper inst{env.vulkan_functions};
inst.CheckCreate();
auto layers = inst.GetActiveLayers(inst.GetPhysDev(), 1);
ASSERT_TRUE(string_eq(layers.at(0).layerName, explicit_layer_name));
}
TEST(ExplicitLayers, ContainsPreInstanceFunctions) {
FrameworkEnvironment env;
env.add_icd(TestICDDetails(TEST_ICD_PATH_VERSION_2_EXPORT_ICD_GPDPA)).add_physical_device({});
const char* explicit_layer_name = "VK_LAYER_enabled_by_override";
env.add_explicit_layer(
ManifestLayer{}.set_file_format_version({1, 1, 2}).add_layer(
ManifestLayer::LayerDescription{}
.set_name(explicit_layer_name)
.set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)
.add_pre_instance_function(ManifestLayer::LayerDescription::FunctionOverride{}
.set_vk_func("vkEnumerateInstanceLayerProperties")
.set_override_name("test_preinst_vkEnumerateInstanceLayerProperties"))
.add_pre_instance_function(ManifestLayer::LayerDescription::FunctionOverride{}
.set_vk_func("vkEnumerateInstanceExtensionProperties")
.set_override_name("test_preinst_vkEnumerateInstanceExtensionProperties"))
.add_pre_instance_function(ManifestLayer::LayerDescription::FunctionOverride{}
.set_vk_func("vkEnumerateInstanceVersion")
.set_override_name("test_preinst_vkEnumerateInstanceVersion"))),
"explicit_test_layer.json");
auto& layer = env.get_test_layer(0);
layer.set_reported_layer_props(34);
layer.set_reported_extension_props(22);
layer.set_reported_instance_version(VK_MAKE_API_VERSION(1, 0, 0, 1));
uint32_t count = 0;
ASSERT_EQ(VK_SUCCESS, env.vulkan_functions.vkEnumerateInstanceLayerProperties(&count, nullptr));
ASSERT_EQ(count, 1U);
count = 0;
ASSERT_EQ(VK_SUCCESS, env.vulkan_functions.vkEnumerateInstanceExtensionProperties(nullptr, &count, nullptr));
ASSERT_EQ(count, 4U);
uint32_t version = 0;
ASSERT_EQ(VK_SUCCESS, env.vulkan_functions.vkEnumerateInstanceVersion(&version));
ASSERT_EQ(version, VK_HEADER_VERSION_COMPLETE);
InstWrapper inst{env.vulkan_functions};
inst.create_info.add_layer(explicit_layer_name);
inst.CheckCreate();
auto layers = inst.GetActiveLayers(inst.GetPhysDev(), 1);
ASSERT_TRUE(string_eq(layers.at(0).layerName, explicit_layer_name));
}
TEST(ExplicitLayers, CallsPreInstanceFunctionsInCreateInstance) {
FrameworkEnvironment env;
env.add_icd(TestICDDetails(TEST_ICD_PATH_VERSION_2_EXPORT_ICD_GPDPA)).add_physical_device({});
const char* explicit_layer_name = "VK_LAYER_enabled_by_override";
env.add_explicit_layer(
ManifestLayer{}.set_file_format_version({1, 1, 2}).add_layer(
ManifestLayer::LayerDescription{}.set_name(explicit_layer_name).set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)),
"explicit_test_layer.json");
auto& layer = env.get_test_layer(0);
layer.set_query_vkEnumerateInstanceLayerProperties(true);
layer.set_query_vkEnumerateInstanceExtensionProperties(true);
layer.set_query_vkEnumerateInstanceVersion(true);
InstWrapper inst{env.vulkan_functions};
inst.create_info.add_layer(explicit_layer_name);
inst.CheckCreate();
auto layers = inst.GetActiveLayers(inst.GetPhysDev(), 1);
ASSERT_TRUE(string_eq(layers.at(0).layerName, explicit_layer_name));
}
// This test makes sure that any layer calling GetPhysicalDeviceProperties2 inside of CreateInstance
// succeeds and doesn't crash.
TEST(LayerCreateInstance, GetPhysicalDeviceProperties2) {
FrameworkEnvironment env;
env.add_icd(TestICDDetails(TEST_ICD_PATH_VERSION_2_EXPORT_ICD_GPDPA))
.add_physical_device({})
.set_icd_api_version(VK_API_VERSION_1_1);
const char* regular_layer_name = "VK_LAYER_TestLayer";
env.add_explicit_layer(
ManifestLayer{}.set_file_format_version({1, 1, 2}).add_layer(
ManifestLayer::LayerDescription{}.set_name(regular_layer_name).set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)),
"regular_test_layer.json");
auto& layer_handle = env.get_test_layer(0);
layer_handle.set_create_instance_callback([](TestLayer& layer) -> VkResult {
uint32_t phys_dev_count = 0;
VkResult res = layer.instance_dispatch_table.EnumeratePhysicalDevices(layer.instance_handle, &phys_dev_count, nullptr);
if (res != VK_SUCCESS || phys_dev_count > 1) {
return VK_ERROR_INITIALIZATION_FAILED; // expecting only a single physical device.
}
VkPhysicalDevice phys_dev{};
res = layer.instance_dispatch_table.EnumeratePhysicalDevices(layer.instance_handle, &phys_dev_count, &phys_dev);
if (res != VK_SUCCESS) {
return VK_ERROR_INITIALIZATION_FAILED;
}
VkPhysicalDeviceProperties2 props2{};
props2.sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_PROPERTIES_2;
layer.instance_dispatch_table.GetPhysicalDeviceProperties2(phys_dev, &props2);
VkPhysicalDeviceFeatures2 features2{};
features2.sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_FEATURES_2;
layer.instance_dispatch_table.GetPhysicalDeviceFeatures2(phys_dev, &features2);
return VK_SUCCESS;
});
InstWrapper inst{env.vulkan_functions};
inst.create_info.add_layer(regular_layer_name).set_api_version(1, 1, 0);
inst.CheckCreate();
}
TEST(LayerCreateInstance, GetPhysicalDeviceProperties2KHR) {
FrameworkEnvironment env;
env.add_icd(TestICDDetails(TEST_ICD_PATH_VERSION_2_EXPORT_ICD_GPDPA))
.add_physical_device({})
.add_instance_extension({"VK_KHR_get_physical_device_properties2", 0});
const char* regular_layer_name = "VK_LAYER_TestLayer";
env.add_explicit_layer(
ManifestLayer{}.add_layer(
ManifestLayer::LayerDescription{}.set_name(regular_layer_name).set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)),
"regular_test_layer.json");
auto& layer_handle = env.get_test_layer(0);
layer_handle.set_create_instance_callback([](TestLayer& layer) -> VkResult {
uint32_t phys_dev_count = 1;
VkPhysicalDevice phys_dev{};
layer.instance_dispatch_table.EnumeratePhysicalDevices(layer.instance_handle, &phys_dev_count, &phys_dev);
VkPhysicalDeviceProperties2KHR props2{};
props2.sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_PROPERTIES_2_KHR;
layer.instance_dispatch_table.GetPhysicalDeviceProperties2KHR(phys_dev, &props2);
VkPhysicalDeviceFeatures2KHR features2{};
features2.sType = VK_STRUCTURE_TYPE_PHYSICAL_DEVICE_FEATURES_2_KHR;
layer.instance_dispatch_table.GetPhysicalDeviceFeatures2KHR(phys_dev, &features2);
return VK_SUCCESS;
});
InstWrapper inst{env.vulkan_functions};
inst.create_info.add_layer(regular_layer_name).add_extension("VK_KHR_get_physical_device_properties2");
inst.CheckCreate();
}
TEST(ExplicitLayers, MultipleLayersInSingleManifest) {
FrameworkEnvironment env;
env.add_icd(TestICDDetails(TEST_ICD_PATH_VERSION_2_EXPORT_ICD_GPDPA)).add_physical_device({});
// verify layer loads successfully when setting VK_LAYER_PATH to a full filepath
const char* regular_layer_name_1 = "VK_LAYER_RegularLayer1";
const char* regular_layer_name_2 = "VK_LAYER_RegularLayer2";
const char* regular_layer_name_3 = "VK_LAYER_RegularLayer3";
env.add_explicit_layer(TestLayerDetails(
ManifestLayer{}
.set_file_format_version({1, 0, 1})
.add_layer(
ManifestLayer::LayerDescription{}.set_name(regular_layer_name_1).set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2))
.add_layer(
ManifestLayer::LayerDescription{}.set_name(regular_layer_name_2).set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2))
.add_layer(
ManifestLayer::LayerDescription{}.set_name(regular_layer_name_3).set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)),
"multi_layer_manifest.json"));
auto layer_props = env.GetLayerProperties(3);
ASSERT_TRUE(string_eq(regular_layer_name_1, layer_props[0].layerName));
ASSERT_TRUE(string_eq(regular_layer_name_2, layer_props[1].layerName));
ASSERT_TRUE(string_eq(regular_layer_name_3, layer_props[2].layerName));
}
TEST(ExplicitLayers, WrapObjects) {
FrameworkEnvironment env;
env.add_icd(TestICDDetails(TEST_ICD_PATH_VERSION_2_EXPORT_ICD_GPDPA)).add_physical_device("physical_device_0");
const char* wrap_objects_name = "VK_LAYER_LUNARG_wrap_objects";
env.add_explicit_layer(ManifestLayer{}.add_layer(
ManifestLayer::LayerDescription{}.set_name(wrap_objects_name).set_lib_path(TEST_LAYER_WRAP_OBJECTS)),
"wrap_objects_layer.json");
const char* regular_layer_name_1 = "VK_LAYER_RegularLayer1";
env.add_explicit_layer(
ManifestLayer{}.add_layer(
ManifestLayer::LayerDescription{}.set_name(regular_layer_name_1).set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)),
"regular_layer_1.json");
const char* regular_layer_name_2 = "VK_LAYER_RegularLayer2";
env.add_explicit_layer(
ManifestLayer{}.add_layer(
ManifestLayer::LayerDescription{}.set_name(regular_layer_name_2).set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)),
"regular_layer_2.json");
{ // just the wrap layer
InstWrapper inst{env.vulkan_functions};
inst.create_info.add_layer(wrap_objects_name);
inst.CheckCreate();
VkPhysicalDevice phys_dev = inst.GetPhysDev();
DeviceWrapper dev{inst};
dev.CheckCreate(phys_dev);
}
{ // wrap layer first
InstWrapper inst{env.vulkan_functions};
inst.create_info.add_layer(wrap_objects_name).add_layer(regular_layer_name_1);
inst.CheckCreate();
VkPhysicalDevice phys_dev = inst.GetPhysDev();
DeviceWrapper dev{inst};
dev.CheckCreate(phys_dev);
}
{ // wrap layer last
InstWrapper inst{env.vulkan_functions};
inst.create_info.add_layer(regular_layer_name_1).add_layer(wrap_objects_name);
inst.CheckCreate();
VkPhysicalDevice phys_dev = inst.GetPhysDev();
DeviceWrapper dev{inst};
dev.CheckCreate(phys_dev);
}
{ // wrap layer last
InstWrapper inst{env.vulkan_functions};
inst.create_info.add_layer(regular_layer_name_1).add_layer(wrap_objects_name).add_layer(regular_layer_name_2);
inst.CheckCreate();
VkPhysicalDevice phys_dev = inst.GetPhysDev();
DeviceWrapper dev{inst};
dev.CheckCreate(phys_dev);
}
}
TEST(ExplicitLayers, VkLayerPathEnvVar) {
FrameworkEnvironment env;
env.add_icd(TestICDDetails(TEST_ICD_PATH_VERSION_2_EXPORT_ICD_GPDPA)).add_physical_device({});
{
// verify layer loads successfully when setting VK_LAYER_PATH to a full filepath
const char* regular_layer_name_1 = "VK_LAYER_RegularLayer1";
env.add_explicit_layer(TestLayerDetails(ManifestLayer{}.add_layer(ManifestLayer::LayerDescription{}
.set_name(regular_layer_name_1)
.set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)),
"regular_layer_1.json")
.set_discovery_type(ManifestDiscoveryType::env_var)
.set_is_dir(false));
InstWrapper inst(env.vulkan_functions);
inst.create_info.add_layer(regular_layer_name_1);
inst.CheckCreate(VK_SUCCESS);
auto layer_props = inst.GetActiveLayers(inst.GetPhysDev(), 1);
EXPECT_TRUE(string_eq(layer_props.at(0).layerName, regular_layer_name_1));
}
{
// verify layers load successfully when setting VK_LAYER_PATH to multiple full filepaths
const char* regular_layer_name_1 = "VK_LAYER_RegularLayer1";
env.add_explicit_layer(TestLayerDetails(ManifestLayer{}.add_layer(ManifestLayer::LayerDescription{}
.set_name(regular_layer_name_1)
.set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)),
"regular_layer_1.json")
.set_discovery_type(ManifestDiscoveryType::env_var)
.set_is_dir(false));
const char* regular_layer_name_2 = "VK_LAYER_RegularLayer2";
env.add_explicit_layer(TestLayerDetails(ManifestLayer{}.add_layer(ManifestLayer::LayerDescription{}
.set_name(regular_layer_name_2)
.set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)),
"regular_layer_2.json")
.set_discovery_type(ManifestDiscoveryType::env_var)
.set_is_dir(false));
InstWrapper inst(env.vulkan_functions);
inst.create_info.add_layer(regular_layer_name_1);
inst.create_info.add_layer(regular_layer_name_2);
inst.CheckCreate(VK_SUCCESS);
auto layer_props = inst.GetActiveLayers(inst.GetPhysDev(), 2);
EXPECT_TRUE(check_permutation({regular_layer_name_1, regular_layer_name_2}, layer_props));
}
{
// verify layers load successfully when setting VK_LAYER_PATH to a directory
const char* regular_layer_name_1 = "VK_LAYER_RegularLayer1";
env.add_explicit_layer(TestLayerDetails(ManifestLayer{}.add_layer(ManifestLayer::LayerDescription{}
.set_name(regular_layer_name_1)
.set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)),
"regular_layer_1.json")
.set_discovery_type(ManifestDiscoveryType::env_var));
const char* regular_layer_name_2 = "VK_LAYER_RegularLayer2";
env.add_explicit_layer(TestLayerDetails(ManifestLayer{}.add_layer(ManifestLayer::LayerDescription{}
.set_name(regular_layer_name_2)
.set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)),
"regular_layer_2.json")
.set_discovery_type(ManifestDiscoveryType::env_var));
InstWrapper inst(env.vulkan_functions);
inst.create_info.add_layer(regular_layer_name_1);
inst.create_info.add_layer(regular_layer_name_2);
inst.CheckCreate(VK_SUCCESS);
auto layer_props = inst.GetActiveLayers(inst.GetPhysDev(), 2);
EXPECT_TRUE(check_permutation({regular_layer_name_1, regular_layer_name_2}, layer_props));
}
}
TEST(ExplicitLayers, DuplicateLayersInVK_LAYER_PATH) {
FrameworkEnvironment env;
env.add_icd(TestICDDetails(TEST_ICD_PATH_VERSION_2_EXPORT_ICD_GPDPA)).add_physical_device({});
// verify layer loads successfully when setting VK_LAYER_PATH to a full filepath
const char* same_layer_name_1 = "VK_LAYER_RegularLayer1";
env.add_explicit_layer(TestLayerDetails(ManifestLayer{}.add_layer(ManifestLayer::LayerDescription{}
.set_name(same_layer_name_1)
.set_description("actually_layer_1")
.set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)),
"regular_layer_1.json")
// use override folder as just a folder and manually set the VK_LAYER_PATH env-var to it
.set_discovery_type(ManifestDiscoveryType::override_folder)
.set_is_dir(true));
auto& layer1 = env.get_test_layer(0);
layer1.set_description("actually_layer_1");
layer1.set_make_spurious_log_in_create_instance("actually_layer_1");
env.env_var_vk_layer_paths.add_to_list(narrow(env.get_folder(ManifestLocation::override_layer).location()));
env.add_explicit_layer(TestLayerDetails(ManifestLayer{}.add_layer(ManifestLayer::LayerDescription{}
.set_name(same_layer_name_1)
.set_description("actually_layer_2")
.set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)),
"regular_layer_1.json")
.set_discovery_type(ManifestDiscoveryType::env_var)
.set_is_dir(true));
auto& layer2 = env.get_test_layer(1);
layer2.set_description("actually_layer_2");
layer2.set_make_spurious_log_in_create_instance("actually_layer_2");
auto layer_props = env.GetLayerProperties(2);
ASSERT_TRUE(string_eq(same_layer_name_1, layer_props[0].layerName));
ASSERT_TRUE(string_eq(same_layer_name_1, layer_props[1].layerName));
ASSERT_TRUE(string_eq(layer1.description.c_str(), layer_props[0].description));
ASSERT_TRUE(string_eq(layer2.description.c_str(), layer_props[1].description));
{
InstWrapper inst{env.vulkan_functions};
inst.create_info.add_layer(same_layer_name_1);
FillDebugUtilsCreateDetails(inst.create_info, env.debug_log);
inst.CheckCreate();
auto enabled_layer_props = inst.GetActiveLayers(inst.GetPhysDev(), 1);
ASSERT_TRUE(string_eq(same_layer_name_1, enabled_layer_props.at(0).layerName));
ASSERT_TRUE(string_eq(layer1.description.c_str(), enabled_layer_props.at(0).description));
ASSERT_TRUE(env.debug_log.find("actually_layer_1"));
ASSERT_FALSE(env.debug_log.find("actually_layer_2"));
}
env.debug_log.clear();
{
EnvVarWrapper layers_enable_env_var{"VK_INSTANCE_LAYERS", same_layer_name_1};
InstWrapper inst{env.vulkan_functions};
FillDebugUtilsCreateDetails(inst.create_info, env.debug_log);
inst.CheckCreate();
auto enabled_layer_props = inst.GetActiveLayers(inst.GetPhysDev(), 1);
ASSERT_TRUE(string_eq(same_layer_name_1, enabled_layer_props.at(0).layerName));
ASSERT_TRUE(string_eq(layer1.description.c_str(), enabled_layer_props.at(0).description));
ASSERT_TRUE(env.debug_log.find("actually_layer_1"));
ASSERT_FALSE(env.debug_log.find("actually_layer_2"));
}
env.debug_log.clear();
{
EnvVarWrapper layers_enable_env_var{"VK_LOADER_LAYERS_ENABLE", same_layer_name_1};
InstWrapper inst{env.vulkan_functions};
FillDebugUtilsCreateDetails(inst.create_info, env.debug_log);
inst.CheckCreate();
auto enabled_layer_props = inst.GetActiveLayers(inst.GetPhysDev(), 1);
ASSERT_TRUE(string_eq(same_layer_name_1, enabled_layer_props.at(0).layerName));
ASSERT_TRUE(string_eq(layer1.description.c_str(), enabled_layer_props.at(0).description));
ASSERT_TRUE(env.debug_log.find("actually_layer_1"));
ASSERT_FALSE(env.debug_log.find("actually_layer_2"));
}
env.debug_log.clear();
}
TEST(ExplicitLayers, DuplicateLayersInVK_ADD_LAYER_PATH) {
FrameworkEnvironment env;
env.add_icd(TestICDDetails(TEST_ICD_PATH_VERSION_2_EXPORT_ICD_GPDPA)).add_physical_device({});
// verify layer loads successfully when setting VK_LAYER_PATH to a full filepath
const char* same_layer_name_1 = "VK_LAYER_RegularLayer1";
env.add_explicit_layer(TestLayerDetails(ManifestLayer{}.add_layer(ManifestLayer::LayerDescription{}
.set_name(same_layer_name_1)
.set_description("actually_layer_1")
.set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)),
"regular_layer_1.json")
// use override folder as just a folder and manually set the VK_ADD_LAYER_PATH env-var to it
.set_discovery_type(ManifestDiscoveryType::override_folder)
.set_is_dir(true));
auto& layer1 = env.get_test_layer(0);
layer1.set_description("actually_layer_1");
layer1.set_make_spurious_log_in_create_instance("actually_layer_1");
env.add_env_var_vk_layer_paths.add_to_list(narrow(env.get_folder(ManifestLocation::override_layer).location()));
env.add_explicit_layer(TestLayerDetails(ManifestLayer{}.add_layer(ManifestLayer::LayerDescription{}
.set_name(same_layer_name_1)
.set_description("actually_layer_2")
.set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)),
"regular_layer_1.json")
.set_discovery_type(ManifestDiscoveryType::add_env_var)
.set_is_dir(true));
auto& layer2 = env.get_test_layer(1);
layer2.set_description("actually_layer_2");
layer2.set_make_spurious_log_in_create_instance("actually_layer_2");
auto layer_props = env.GetLayerProperties(2);
ASSERT_TRUE(string_eq(same_layer_name_1, layer_props[0].layerName));
ASSERT_TRUE(string_eq(same_layer_name_1, layer_props[1].layerName));
ASSERT_TRUE(string_eq(layer1.description.c_str(), layer_props[0].description));
ASSERT_TRUE(string_eq(layer2.description.c_str(), layer_props[1].description));
{
InstWrapper inst{env.vulkan_functions};
inst.create_info.add_layer(same_layer_name_1);
FillDebugUtilsCreateDetails(inst.create_info, env.debug_log);
inst.CheckCreate();
auto enabled_layer_props = inst.GetActiveLayers(inst.GetPhysDev(), 1);
ASSERT_TRUE(string_eq(same_layer_name_1, enabled_layer_props.at(0).layerName));
ASSERT_TRUE(string_eq(layer1.description.c_str(), enabled_layer_props.at(0).description));
ASSERT_TRUE(env.debug_log.find("actually_layer_1"));
ASSERT_FALSE(env.debug_log.find("actually_layer_2"));
}
env.debug_log.clear();
{
EnvVarWrapper layers_enable_env_var{"VK_INSTANCE_LAYERS", same_layer_name_1};
InstWrapper inst{env.vulkan_functions};
FillDebugUtilsCreateDetails(inst.create_info, env.debug_log);
inst.CheckCreate();
auto enabled_layer_props = inst.GetActiveLayers(inst.GetPhysDev(), 1);
ASSERT_TRUE(string_eq(same_layer_name_1, enabled_layer_props.at(0).layerName));
ASSERT_TRUE(string_eq(layer1.description.c_str(), enabled_layer_props.at(0).description));
ASSERT_TRUE(env.debug_log.find("actually_layer_1"));
ASSERT_FALSE(env.debug_log.find("actually_layer_2"));
}
env.debug_log.clear();
{
EnvVarWrapper layers_enable_env_var{"VK_LOADER_LAYERS_ENABLE", same_layer_name_1};
InstWrapper inst{env.vulkan_functions};
FillDebugUtilsCreateDetails(inst.create_info, env.debug_log);
inst.CheckCreate();
auto enabled_layer_props = inst.GetActiveLayers(inst.GetPhysDev(), 1);
ASSERT_TRUE(string_eq(same_layer_name_1, enabled_layer_props.at(0).layerName));
ASSERT_TRUE(string_eq(layer1.description.c_str(), enabled_layer_props.at(0).description));
ASSERT_TRUE(env.debug_log.find("actually_layer_1"));
ASSERT_FALSE(env.debug_log.find("actually_layer_2"));
}
env.debug_log.clear();
}
TEST(ExplicitLayers, CorrectOrderOfEnvVarEnabledLayers) {
FrameworkEnvironment env;
env.add_icd(TestICDDetails(TEST_ICD_PATH_VERSION_2_EXPORT_ICD_GPDPA)).add_physical_device({});
// verify layer loads successfully when setting VK_LAYER_PATH to a full filepath
const char* layer_name_1 = "VK_LAYER_RegularLayer1";
env.add_explicit_layer(TestLayerDetails(ManifestLayer{}.add_layer(ManifestLayer::LayerDescription{}
.set_name(layer_name_1)
.set_description("actually_layer_1")
.set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)),
"regular_layer_1.json")
.set_discovery_type(ManifestDiscoveryType::env_var)
.set_is_dir(true));
auto& layer1 = env.get_test_layer(0);
layer1.set_description("actually_layer_1");
const char* layer_name_2 = "VK_LAYER_RegularLayer2";
env.add_explicit_layer(TestLayerDetails(ManifestLayer{}.add_layer(ManifestLayer::LayerDescription{}
.set_name(layer_name_2)
.set_description("actually_layer_2")
.set_lib_path(TEST_LAYER_PATH_EXPORT_VERSION_2)),