OpenGL 输入结构对齐
Uniform 缓冲对象 (Uniform Buffer Object)
OpenGL 中的分类
需要传几个数字/矩阵? → Uniform
需要传几十个材质参数/相机矩阵(多个 Shader 共享)? → UBO
需要传模型的形状数据(几万个顶点)? → VBO
需要传海量的查询表或图像? → Texture
需要传百万级的光源/粒子,且需要 GPU 参与计算和修改? → SSBO
UBO / SSBO 需要内存对齐
| GLSL 数据类型 | std140 (UBO) 基础对齐量 | std430 (SSBO) 基础对齐量 | 差异点分析 |
|---|---|---|---|
float, int, bool |
4 字节 | 4 字节 | 无区别。 |
vec2 |
8 字节 | 8 字节 | 无区别。 |
vec3 |
16 字节 | 16 字节 | 无区别!这是最大的坑! 哪怕是 std430,vec3 也必须按 16 字节对齐,这意味着它后面永远跟着 4 字节的废料。 |
vec4 |
16 字节 | 16 字节 | 无区别。 |
float 数组 (float[N]) |
16 字节 (强制) | 4 字节 | 巨大差异! std140 会把数组的每个元素强行拉伸到 vec4 大小;std430 则保持紧凑。 |
结构体 (struct) |
内部最大对齐量,且强制进位到 16 的倍数 | 内部最大元素的对齐量 | 差异很大! std140 结尾必然填充到 16 字节倍数;std430 不需要强制 16 字节收尾(除非内部有 vec4)。 |
mat4 (按列主序) |
16 字节 (视为 4 个 vec4) |
16 字节 | 无区别。大小都是 64 字节。 |
本博客所有文章除特别声明外,均采用 CC BY-NC-SA 4.0 许可协议。转载请注明来源 Never Settle!
评论