优化内存读取

This commit is contained in:
xsl
2025-11-29 11:35:56 +08:00
parent 9c71e40c97
commit 1859706412
814 changed files with 911 additions and 128 deletions
+45 -33
View File
@@ -641,24 +641,31 @@ uint32_t Application::findMemoryType(VkPhysicalDevice physicalDevice, uint32_t t
throw std::runtime_error("Failed to find suitable memory type!");
}
Texture Application::loadTexture(std::string path, Texture& tex, bool srgb)
void Application::loadTexture(std::string path, Texture& tex, bool srgb)
{
std::vector<unsigned char> data = readFileUnsignedChar(path, false);
std::vector<unsigned char> image;
unsigned w, h;
unsigned error = lodepng::decode(image, w, h, data, LCT_RGBA, 8);
processWithVulkan(image.data(), w, h, w * 4, image.size(), tex, srgb);
return tex;
//return tex;
}
void Application::loadTexture(std::vector<unsigned char>& image_data, size_t image_size, int w, int h, Texture& tex, bool srgb)
{
processWithVulkan(image_data.data(), w, h, w * 4, image_size, tex, srgb);
//return tex;
}
#ifdef _WIN32
Texture Application::loadTextureExample(std::wstring path, Texture& tex, bool srgb)
void Application::loadTextureExample(std::wstring path, Texture& tex, bool srgb)
{
std::vector<unsigned char> data = readFileUnsignedCharWin32(path, true);
std::vector<unsigned char> image;
unsigned w, h;
unsigned error = lodepng::decode(image, w, h, data, LCT_RGBA, 8);
processWithVulkan(image.data(), w, h, w * 4, image.size(), tex, srgb);
return tex;
//return tex;
}
#endif // _WIN32
@@ -762,6 +769,7 @@ void Application::createTexture(VkDevice device, VkPhysicalDevice physicalDevice
}
texture.image_layout = VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL;
texture.device = device;
}
void Application::processWithVulkan(uint8_t* data, int width, int height, int rowStride, size_t dataSize, Texture& out_texture, bool srgb)
@@ -820,38 +828,44 @@ void Application::updateTexture(VkDevice device, VkPhysicalDevice physicalDevice
uint8_t* data, int width, int height,
int rowStride, size_t dataSize, Texture& texture)
{
VkBuffer stagingBuffer;
VkDeviceMemory stagingBufferMemory;
//VkBuffer stagingBuffer;
//VkDeviceMemory stagingBufferMemory;
VkBufferCreateInfo bufferInfo = {};
bufferInfo.sType = VK_STRUCTURE_TYPE_BUFFER_CREATE_INFO;
bufferInfo.size = dataSize;
bufferInfo.usage = VK_BUFFER_USAGE_TRANSFER_SRC_BIT;
bufferInfo.sharingMode = VK_SHARING_MODE_EXCLUSIVE;
if (vkCreateBuffer(device, &bufferInfo, nullptr, &stagingBuffer) != VK_SUCCESS)
if (texture.stagingBuffer == nullptr)
{
throw std::runtime_error("Failed to create staging buffer!");
VkBufferCreateInfo bufferInfo = {};
bufferInfo.sType = VK_STRUCTURE_TYPE_BUFFER_CREATE_INFO;
bufferInfo.size = dataSize;
bufferInfo.usage = VK_BUFFER_USAGE_TRANSFER_SRC_BIT;
bufferInfo.sharingMode = VK_SHARING_MODE_EXCLUSIVE;
if (vkCreateBuffer(device, &bufferInfo, nullptr, &texture.stagingBuffer) != VK_SUCCESS)
{
throw std::runtime_error("Failed to create staging buffer!");
}
}
VkMemoryRequirements memRequirements;
vkGetBufferMemoryRequirements(device, stagingBuffer, &memRequirements);
VkMemoryAllocateInfo allocInfo = {};
allocInfo.sType = VK_STRUCTURE_TYPE_MEMORY_ALLOCATE_INFO;
allocInfo.allocationSize = memRequirements.size;
allocInfo.memoryTypeIndex = findMemoryType(physicalDevice,
memRequirements.memoryTypeBits, VK_MEMORY_PROPERTY_HOST_VISIBLE_BIT | VK_MEMORY_PROPERTY_HOST_COHERENT_BIT);
if (vkAllocateMemory(device, &allocInfo, nullptr, &stagingBufferMemory) != VK_SUCCESS)
if (texture.stagingBufferMemory == nullptr)
{
throw std::runtime_error("Failed to allocate staging buffer memory!");
}
VkMemoryRequirements memRequirements;
vkGetBufferMemoryRequirements(device, texture.stagingBuffer, &memRequirements);
vkBindBufferMemory(device, stagingBuffer, stagingBufferMemory, 0);
VkMemoryAllocateInfo allocInfo = {};
allocInfo.sType = VK_STRUCTURE_TYPE_MEMORY_ALLOCATE_INFO;
allocInfo.allocationSize = memRequirements.size;
allocInfo.memoryTypeIndex = findMemoryType(physicalDevice,
memRequirements.memoryTypeBits, VK_MEMORY_PROPERTY_HOST_VISIBLE_BIT | VK_MEMORY_PROPERTY_HOST_COHERENT_BIT);
if (vkAllocateMemory(device, &allocInfo, nullptr, &texture.stagingBufferMemory) != VK_SUCCESS)
{
throw std::runtime_error("Failed to allocate staging buffer memory!");
}
vkBindBufferMemory(device, texture.stagingBuffer, texture.stagingBufferMemory, 0);
}
void* mappedData;
vkMapMemory(device, stagingBufferMemory, 0, dataSize, 0, &mappedData);
vkMapMemory(device, texture.stagingBufferMemory, 0, dataSize, 0, &mappedData);
if (rowStride == width * 4)
{
@@ -871,7 +885,7 @@ void Application::updateTexture(VkDevice device, VkPhysicalDevice physicalDevice
}
}
vkUnmapMemory(device, stagingBufferMemory);
vkUnmapMemory(device, texture.stagingBufferMemory);
VkCommandBuffer commandBuffer = beginSingleTimeCommands(device, commandPool);
@@ -891,7 +905,7 @@ void Application::updateTexture(VkDevice device, VkPhysicalDevice physicalDevice
region.imageExtent = { static_cast<uint32_t>(width),
static_cast<uint32_t>(height), 1 };
vkCmdCopyBufferToImage(commandBuffer, stagingBuffer, texture.image,
vkCmdCopyBufferToImage(commandBuffer, texture.stagingBuffer, texture.image,
VK_IMAGE_LAYOUT_TRANSFER_DST_OPTIMAL, 1, &region);
transitionImageLayout(commandBuffer, texture.image,
@@ -900,8 +914,6 @@ void Application::updateTexture(VkDevice device, VkPhysicalDevice physicalDevice
endSingleTimeCommands(device, commandPool, queue, commandBuffer);
vkDestroyBuffer(device, stagingBuffer, nullptr);
vkFreeMemory(device, stagingBufferMemory, nullptr);
texture.image_layout = VK_IMAGE_LAYOUT_SHADER_READ_ONLY_OPTIMAL;
}