Files
obsidian-notes/3Resources/游戏开发/性能优化/卡片/通过Unity申请的RenderTexture的内存在显存中还是在内存中.md
zzzisfunnyboy ab75441581
2025-11-28 08:44:02 +08:00

89 lines
2.3 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

---
tags:
- Texture
- Texture2D
- RenderTexture
---
# 总结
- **RenderTexture 的像素数据 100% 在显存GPU Memory中**,不是在 CPU 内存中。
- 除非**触发回读CPU**也就是ReadPixel才会在内存中有数据
- 内存中有RT对象、Unity C++中的handle
下面分层说明其放在哪里、为什么、以及哪些部分可能在 CPU。
---
# 1. **RenderTexture 的核心像素存储位置:显存 (VRAM)**
Unity 调用底层 APIDX11/12、Metal、Vulkan、GLES创建 RenderTarget Texture 一定会将纹理 Allocation 放在:
- **VRAMGPU local memory**
- 或在某些平台(集显)上在**统一显存 UMA**区域(但本质也属于 GPU 可直接访问的物理内存)
因为:
### RenderTexture 必须支持:
- GPU 作为 RenderTarget 写入
- GPU 作为 Shader 资源读
- ComputeShader random write开启 enableRandomWrite 时)
这些都要求纹理在 GPU 可直接寻址的专用显存中。
**所以 RenderTexture 不会放在 CPU 内存System RAM。**
---
# 2. 那系统内存会占用吗?
会,但只是**少量管理结构**
|类型|是否在 CPU RAM|说明|
|---|---|---|
|RenderTexture 对象C# wrapper|✔|占用极小(几十字节)|
|Unity 内部 RenderTexture handle|✔|也非常小|
|像素数据|✖|全在显存|
**像素数据绝不会放在 System RAM。**
除非你用 `ReadPixels` 强制拷贝。
---
# 3. 特殊情况(集显、移动设备)
即便 CPU 和 GPU 共用物理内存(如 Intel 集显、移动 SOCUnity 仍然会:
- 将 RenderTexture 创建成 **GPU 访问区域的纹理资源**
- 不会放到 CPU 那边的缓冲区
因此逻辑上它依然属于“显存”。
---
# 4. 如果你读取 RenderTexture会发生什么
例如:
`RenderTexture.active = rt; tex.ReadPixels(...);`
**这会把 RenderTexture 从 GPU → CPU 进行一次拷贝**
代价巨大,会 stall GPU → CPU pipeline。
但这只是“做了 CPU 副本”RenderTexture 仍然在显存中。
---
# 5. Unity Profiler 中的 Attrib
Profiler 中 GPU Memory 的 **RenderTexture** 项目,就是 VRAM 占用。
CPU Memory 中不会出现它。
如果你看到 CPU Memory 涨,是你创建了大量 Texture2D Readback 副本。