我正在尝试初始化Vulkan API
我遇到的问题是,在拨打vkCreateInstance
后我收到了访问冲突错误,我认为问题来自扩展名和图层列表。
我使用char buff [20] [256]将它们从字符串传递到API调用的结构,我在调试器中看到的层和扩展名(3个扩展和15个层)都比256短得多字符和全部为空终止
扩展名或图层名称没有缓冲区溢出,但它崩溃了。
我之前使用vkEnumerateInstanceExtensionProperties
和vkEnumerateInstanceLayerProperties
收到的字符串的图层和扩展名列表,都是有效的以空字符结尾的字符串,例如" VK_KHR_surface"等等。
即使它说我支持某些扩展,我也不可能真的支持它们,并且当它试图初始化我不支持的扩展时API会崩溃吗?
void InitializeInstance(void** instance, const vector<string>& layers, const vector<string>& extensions)
{
VkApplicationInfo applicationInfo;
VkInstanceCreateInfo instanceInfo;
VkInstance* instanceOut = (VkInstance*)instance;
applicationInfo.sType = VK_STRUCTURE_TYPE_APPLICATION_INFO;
applicationInfo.pNext = nullptr;
applicationInfo.pApplicationName = "MyApp";
applicationInfo.pEngineName = "MyEngine";
applicationInfo.engineVersion = 1;
applicationInfo.apiVersion = VK_API_VERSION_1_0;
instanceInfo.sType = VK_STRUCTURE_TYPE_INSTANCE_CREATE_INFO;
instanceInfo.pNext = null;
instanceInfo.flags = 0;
instanceInfo.pApplicationInfo = &applicationInfo;
char buffLayer[20][256];
char buffExt[20][256];
if(!layers.empty())
{
instanceInfo.enabledLayerCount = layers.size();
for(int i = 0; i < layers.size(); i++)
{
strcpy(buffLayer[i], layers[i].c_str());
}
instanceInfo.ppEnabledLayerNames = (char**)buffLayer;
}
else
{
instanceInfo.enabledLayerCount = 0;
instanceInfo.ppEnabledLayerNames = nullptr;
}
if(!extensions.empty())
{
instanceInfo.enabledExtensionCount = extensions.size();
for(int i = 0; i < extensions.size(); i++)
{
strcpy(buffExt[i], extensions[i].c_str());
}
instanceInfo.ppEnabledExtensionNames = (char**)buffExt;
}
else
{
instanceInfo.enabledExtensionCount = 0;
instanceInfo.ppEnabledExtensionNames = nullptr;
}
vkCreateInstance(&instanceInfo, nullptr, instanceOut);
}
当我只有0个扩展名和0个图层时,它会成功创建。如果它们中的任何一个不为0,它就会崩溃。
答案 0 :(得分:2)
char buffLayer[20][256];
instanceInfo.ppEnabledLayerNames = (char**)buffLayer;
ppEnabledLayerNames应该是指针到字符数组的数组。但是你传递的是2D字符数组,实际上只是一个20 * 256个字符的数组。
如果你在一台具有32位指针的机器上,驱动程序将采用buffLayer中的前四个字节并将它们视为指向字符数组的指针。但是你刚刚存储了图层名称的前四个字符,'VK_K'可能不会是一个有效的指针值:)。因此,当尝试取消引用该无效指针时,加载程序将崩溃。
最简单的改变可能是添加:
char* layerNames[20];
for (int i = 0; i < 20; i++)
layerNames[i] = &buffLayer[i][0];
并将layerNames传递为ppEnabledLayerNames。