Vulkan 内存堆及其内存类型

Vulkan memoryHeaps and their memoryTypes

上图总结了我对 memoryHeap 及其由 Vulkan 为给定系统设置生成的 memoryTypes 的理解。感谢@NicolBolas , , and an answer by @krOoze 分享的有关此主题的答案。

不过,我还有一些悬而未决的问题我喜欢的帮助,我已将它们标为红色 并在下面根据@NicolBolas 的评论进行了详细说明。

问题

  1. 为什么只有 4 个 RAM 时 sysRam 中有 9 个 memoryType? 每种内存类型的物理意义是什么?如何使用每个 这些内存类型?

  2. 为什么 GPU RAM 有两种内存类型?这是否意味着每个 GPU RAM 的 memoryType 是 6144MB/2 = 3072MB?

  3. 每种内存类型是否有大小限制?如果是,如何发现 他们的极限?
  4. 为什么 Vulkan 和 cat 报告空闲内存 /proc/meminfo 不同?

提前感谢您的帮助。

在询问 driver 之前,您对 Vulkan 中的内存类型一无所知。

我觉得你最大的误解就是内存类型在物理上是分开的。如图所示,你有两个内存堆,假设 0 是 CPU 内存,1 是 GPU。在这些堆中,您有不同的内存类型。每种内存类型在自己的堆中占用 space,并且可以使用所有堆 space 或与其他类型共享。对于每种类型,您将有不同的内部分配方法,具有不同的对齐要求和不同的允许用途。有多个与内存类型相关的查询,包括 vkGetBufferMemoryRequirements、vkGetImageMemoryRequirements 等。这完全取决于您使用内存的目的。

此外,这些内存类型 driver 依赖,并且会因供应商而异(看起来像当前的 nVidia 布局)。

Why are there 9 memoryType in sysRam when there are only 4x RAMs? What is the physical meaning of each memoryType? How to use each of these memoryType?

Why are there 2 memory types for GPU RAM?

我不知道你所说的“4x RAM”是什么意思;我怀疑您是在谈论您的机器中有多少物理记忆棒。内存类型(或堆)不关心这些事情。

至于其他,记住内存在 Vulkan 中的工作原理始终很重要。堆在某种程度上代表实际的物理 RAM。内存类型表示分配该内存的方式。但是 使用 内存有自己的内存类型限制。

例如,如果图像具有颜色附件使用参数,实施可以强制您使用特定的内存类型作为支持该图像的内存。没有颜色附件的图像可以限制使用其他内存类型,但不能使用 that 一种。等等。

显然,。仅仅查询可用的内存类型不足以了解如何分配内存。您必须弄清楚您将使用哪些缓冲区和图像(包括格式和使用参数)。然后你要查询实现对他们有什么限制。

您的应用程序必须适应这些限制。

Is there a size limit to each memoryTypes?

说不定有这种东西。 后者是内存堆的工作。

Why are the free memory reported by Vulkan and cat /proc/meminfo different?

Vulkan 没有 API 报告空闲内存,只有 内存。询问可用内存的数量是愚蠢的。内存(或者至少是应用程序中的虚拟页面)由应用程序中的所有线程共享。尤其是 GPU 内存在机器上的所有进程之间共享。当您得到答复时,内存量可能已经改变。因此,当您根据被告知可用的内容去分配内存时,它可能不再可用了。

最好先分配,如果发生分配失败再处理。

您可以询问总内存,以便决定如何分配内存块。但这就是您确定可用和不可用的方式,而不是通过查询尺寸。

[metaquestion] Why is X in Vulkan?

因为Vulkan规范允许。休息是实施细节,只有 implementer\vendor 才能确定,并且可能取决于他睡得有多好。

  1. Why are there 9 memoryType in sysRam when there are only 4x RAMs? What is the physical meaning of each memoryType? How to use each of these memoryType?

已在 中回答。一个用于 VkBuffers,一个用于 VkImages,每个深度格式一个(即 7)。等于 9;谜底揭晓。

  1. Why are there 2 memory types for GPU RAM? Does this mean each memoryType of the GPU RAM is 6144MB/2 = 3072MB?

可能与 1 类似的原因。我推测一个用于 VkBuffers,一个用于 VkImages。 NVIDIA 的人可以用 vkGetXMemoryRequirements.

进行测试

不一定是RAM/2。这并非完全不可能,但如果是这样的话,实施者应该再次公开单独的堆。

  1. Is there a size limit to each memoryTypes? If yes, how to discover their limits?

大致是堆大小。由于碎片化,您可能会得到更少。并且由于其他进程共享相同的。您的 impl 也可能会为其内部需求分配一些自身。

当你得到 VK_ERROR_OUT_OF_DEVICE_MEMORY 时,你就发现了极限。 (顺便说一句,大部分工作与 CPU 方面相同,在那里你得到 bad_alloc)。

单个分配的大小有限制(不建议分配 > 4 GB),分配的数量也有限制(maxMemoryAllocationCount)。

  1. Why are the free memory reported by Vulkan and cat /proc/meminfo different?

AFAIK Vulkan 不报告空闲内存。 VkMemoryHeap 显示 内存:

size is the total memory size in bytes in the heap.