nir/vtn: add support for SpvBuiltInGlobalLinearId
v2: use formula with fewer operations Signed-off-by: Karol Herbst <kherbst@redhat.com> Reviewed-by: Jason Ekstrand <jason@jlekstrand.net> Reviewed-by: Bas Nieuwenhuizen <bas@basnieuwenhuizen.nl>
This commit is contained in:
@@ -1860,6 +1860,8 @@ nir_intrinsic_from_system_value(gl_system_value val)
|
||||
return nir_intrinsic_load_local_group_size;
|
||||
case SYSTEM_VALUE_GLOBAL_INVOCATION_ID:
|
||||
return nir_intrinsic_load_global_invocation_id;
|
||||
case SYSTEM_VALUE_GLOBAL_INVOCATION_INDEX:
|
||||
return nir_intrinsic_load_global_invocation_index;
|
||||
case SYSTEM_VALUE_WORK_DIM:
|
||||
return nir_intrinsic_load_work_dim;
|
||||
default:
|
||||
|
@@ -533,6 +533,7 @@ system_value("num_subgroups", 1)
|
||||
system_value("subgroup_id", 1)
|
||||
system_value("local_group_size", 3)
|
||||
system_value("global_invocation_id", 3, bit_sizes=[32, 64])
|
||||
system_value("global_invocation_index", 1, bit_sizes=[32, 64])
|
||||
system_value("work_dim", 1)
|
||||
# Driver-specific viewport scale/offset parameters.
|
||||
#
|
||||
|
@@ -99,6 +99,29 @@ build_local_invocation_id(nir_builder *b, unsigned bit_size)
|
||||
}
|
||||
}
|
||||
|
||||
static nir_ssa_def*
|
||||
build_global_group_size(nir_builder *b, unsigned bit_size)
|
||||
{
|
||||
nir_ssa_def *group_size = build_local_group_size(b, bit_size);
|
||||
nir_ssa_def *num_work_groups = nir_u2u(b, nir_load_num_work_groups(b), bit_size);
|
||||
return nir_imul(b, group_size, num_work_groups);
|
||||
}
|
||||
|
||||
static nir_ssa_def*
|
||||
build_global_invocation_id(nir_builder *b, unsigned bit_size)
|
||||
{
|
||||
/* From the GLSL man page for gl_GlobalInvocationID:
|
||||
*
|
||||
* "The value of gl_GlobalInvocationID is equal to
|
||||
* gl_WorkGroupID * gl_WorkGroupSize + gl_LocalInvocationID"
|
||||
*/
|
||||
nir_ssa_def *group_size = build_local_group_size(b, bit_size);
|
||||
nir_ssa_def *group_id = nir_u2u(b, nir_load_work_group_id(b), bit_size);
|
||||
nir_ssa_def *local_id = build_local_invocation_id(b, bit_size);
|
||||
|
||||
return nir_iadd(b, nir_imul(b, group_id, group_size), local_id);
|
||||
}
|
||||
|
||||
static bool
|
||||
convert_block(nir_block *block, nir_builder *b)
|
||||
{
|
||||
@@ -133,16 +156,20 @@ convert_block(nir_block *block, nir_builder *b)
|
||||
nir_ssa_def *sysval = NULL;
|
||||
switch (var->data.location) {
|
||||
case SYSTEM_VALUE_GLOBAL_INVOCATION_ID: {
|
||||
/* From the GLSL man page for gl_GlobalInvocationID:
|
||||
*
|
||||
* "The value of gl_GlobalInvocationID is equal to
|
||||
* gl_WorkGroupID * gl_WorkGroupSize + gl_LocalInvocationID"
|
||||
*/
|
||||
nir_ssa_def *group_size = build_local_group_size(b, bit_size);
|
||||
nir_ssa_def *group_id = nir_u2u(b, nir_load_work_group_id(b), bit_size);
|
||||
nir_ssa_def *local_id = build_local_invocation_id(b, bit_size);
|
||||
sysval = build_global_invocation_id(b, bit_size);
|
||||
break;
|
||||
}
|
||||
|
||||
sysval = nir_iadd(b, nir_imul(b, group_id, group_size), local_id);
|
||||
case SYSTEM_VALUE_GLOBAL_INVOCATION_INDEX: {
|
||||
nir_ssa_def *global_id = build_global_invocation_id(b, bit_size);
|
||||
nir_ssa_def *global_size = build_global_group_size(b, bit_size);
|
||||
|
||||
/* index = id.x + ((id.y + (id.z * size.y)) * size.x) */
|
||||
sysval = nir_imul(b, nir_channel(b, global_id, 2),
|
||||
nir_channel(b, global_size, 1));
|
||||
sysval = nir_iadd(b, nir_channel(b, global_id, 1), sysval);
|
||||
sysval = nir_imul(b, nir_channel(b, global_size, 0), sysval);
|
||||
sysval = nir_iadd(b, nir_channel(b, global_id, 0), sysval);
|
||||
break;
|
||||
}
|
||||
|
||||
@@ -259,9 +286,7 @@ convert_block(nir_block *block, nir_builder *b)
|
||||
break;
|
||||
|
||||
case SYSTEM_VALUE_GLOBAL_GROUP_SIZE: {
|
||||
nir_ssa_def *group_size = build_local_group_size(b, bit_size);
|
||||
nir_ssa_def *num_work_groups = nir_u2u(b, nir_load_num_work_groups(b), bit_size);
|
||||
sysval = nir_imul(b, group_size, num_work_groups);
|
||||
sysval = build_global_group_size(b, bit_size);
|
||||
break;
|
||||
}
|
||||
|
||||
|
@@ -600,6 +600,7 @@ typedef enum
|
||||
SYSTEM_VALUE_LOCAL_INVOCATION_ID,
|
||||
SYSTEM_VALUE_LOCAL_INVOCATION_INDEX,
|
||||
SYSTEM_VALUE_GLOBAL_INVOCATION_ID,
|
||||
SYSTEM_VALUE_GLOBAL_INVOCATION_INDEX,
|
||||
SYSTEM_VALUE_WORK_GROUP_ID,
|
||||
SYSTEM_VALUE_NUM_WORK_GROUPS,
|
||||
SYSTEM_VALUE_LOCAL_GROUP_SIZE,
|
||||
|
@@ -1337,6 +1337,10 @@ vtn_get_builtin_location(struct vtn_builder *b,
|
||||
*location = SYSTEM_VALUE_GLOBAL_INVOCATION_ID;
|
||||
set_mode_system_value(b, mode);
|
||||
break;
|
||||
case SpvBuiltInGlobalLinearId:
|
||||
*location = SYSTEM_VALUE_GLOBAL_INVOCATION_INDEX;
|
||||
set_mode_system_value(b, mode);
|
||||
break;
|
||||
case SpvBuiltInBaseVertex:
|
||||
/* OpenGL gl_BaseVertex (SYSTEM_VALUE_BASE_VERTEX) is not the same
|
||||
* semantic as SPIR-V BaseVertex (SYSTEM_VALUE_FIRST_VERTEX).
|
||||
|
Reference in New Issue
Block a user