diff --git a/src/compiler/nir/nir.h b/src/compiler/nir/nir.h index 971d8c4979f..0042f803eb2 100644 --- a/src/compiler/nir/nir.h +++ b/src/compiler/nir/nir.h @@ -1292,9 +1292,11 @@ typedef struct { /** number of components of each input register * * If this value is 0, the number of components is given by the - * num_components field of nir_intrinsic_instr. + * num_components field of nir_intrinsic_instr. If this value is -1, the + * intrinsic consumes however many components are provided and it is not + * validated at all. */ - unsigned src_components[NIR_INTRINSIC_MAX_INPUTS]; + int src_components[NIR_INTRINSIC_MAX_INPUTS]; bool has_dest; @@ -1322,10 +1324,12 @@ nir_intrinsic_src_components(nir_intrinsic_instr *intr, unsigned srcn) { const nir_intrinsic_info *info = &nir_intrinsic_infos[intr->intrinsic]; assert(srcn < info->num_srcs); - if (info->src_components[srcn]) + if (info->src_components[srcn] > 0) return info->src_components[srcn]; - else + else if (info->src_components[srcn] == 0) return intr->num_components; + else + return nir_src_num_components(intr->src[srcn]); } static inline unsigned diff --git a/src/compiler/nir/nir_intrinsics.py b/src/compiler/nir/nir_intrinsics.py index 6ea6ad1198f..24bcd6bb169 100644 --- a/src/compiler/nir/nir_intrinsics.py +++ b/src/compiler/nir/nir_intrinsics.py @@ -132,9 +132,9 @@ intrinsic("nop", flags=[CAN_ELIMINATE]) intrinsic("load_param", dest_comp=0, indices=[PARAM_IDX], flags=[CAN_ELIMINATE]) -intrinsic("load_deref", dest_comp=0, src_comp=[1], flags=[CAN_ELIMINATE]) -intrinsic("store_deref", src_comp=[1, 0], indices=[WRMASK]) -intrinsic("copy_deref", src_comp=[1, 1]) +intrinsic("load_deref", dest_comp=0, src_comp=[-1], flags=[CAN_ELIMINATE]) +intrinsic("store_deref", src_comp=[-1, 0], indices=[WRMASK]) +intrinsic("copy_deref", src_comp=[-1, -1]) # Interpolation of input. The interp_deref_at* intrinsics are similar to the # load_var intrinsic acting on a shader input except that they interpolate the @@ -269,15 +269,15 @@ intrinsic("set_vertex_count", src_comp=[1]) # lowered, variants take a constant buffer index and register offset. def atomic(name, flags=[]): - intrinsic(name + "_deref", src_comp=[1], dest_comp=1, flags=flags) + intrinsic(name + "_deref", src_comp=[-1], dest_comp=1, flags=flags) intrinsic(name, src_comp=[1], dest_comp=1, indices=[BASE], flags=flags) def atomic2(name): - intrinsic(name + "_deref", src_comp=[1, 1], dest_comp=1) + intrinsic(name + "_deref", src_comp=[-1, 1], dest_comp=1) intrinsic(name, src_comp=[1, 1], dest_comp=1, indices=[BASE]) def atomic3(name): - intrinsic(name + "_deref", src_comp=[1, 1, 1], dest_comp=1) + intrinsic(name + "_deref", src_comp=[-1, 1, 1], dest_comp=1) intrinsic(name, src_comp=[1, 1, 1], dest_comp=1, indices=[BASE]) atomic("atomic_counter_inc") @@ -374,20 +374,20 @@ intrinsic("vulkan_resource_reindex", src_comp=[1, 1], dest_comp=1, # 1: The data parameter to the atomic function (i.e. the value to add # in shared_atomic_add, etc). # 2: For CompSwap only: the second data parameter. -intrinsic("deref_atomic_add", src_comp=[1, 1], dest_comp=1) -intrinsic("deref_atomic_imin", src_comp=[1, 1], dest_comp=1) -intrinsic("deref_atomic_umin", src_comp=[1, 1], dest_comp=1) -intrinsic("deref_atomic_imax", src_comp=[1, 1], dest_comp=1) -intrinsic("deref_atomic_umax", src_comp=[1, 1], dest_comp=1) -intrinsic("deref_atomic_and", src_comp=[1, 1], dest_comp=1) -intrinsic("deref_atomic_or", src_comp=[1, 1], dest_comp=1) -intrinsic("deref_atomic_xor", src_comp=[1, 1], dest_comp=1) -intrinsic("deref_atomic_exchange", src_comp=[1, 1], dest_comp=1) -intrinsic("deref_atomic_comp_swap", src_comp=[1, 1, 1], dest_comp=1) -intrinsic("deref_atomic_fadd", src_comp=[1, 1], dest_comp=1) -intrinsic("deref_atomic_fmin", src_comp=[1, 1], dest_comp=1) -intrinsic("deref_atomic_fmax", src_comp=[1, 1], dest_comp=1) -intrinsic("deref_atomic_fcomp_swap", src_comp=[1, 1, 1], dest_comp=1) +intrinsic("deref_atomic_add", src_comp=[-1, 1], dest_comp=1) +intrinsic("deref_atomic_imin", src_comp=[-1, 1], dest_comp=1) +intrinsic("deref_atomic_umin", src_comp=[-1, 1], dest_comp=1) +intrinsic("deref_atomic_imax", src_comp=[-1, 1], dest_comp=1) +intrinsic("deref_atomic_umax", src_comp=[-1, 1], dest_comp=1) +intrinsic("deref_atomic_and", src_comp=[-1, 1], dest_comp=1) +intrinsic("deref_atomic_or", src_comp=[-1, 1], dest_comp=1) +intrinsic("deref_atomic_xor", src_comp=[-1, 1], dest_comp=1) +intrinsic("deref_atomic_exchange", src_comp=[-1, 1], dest_comp=1) +intrinsic("deref_atomic_comp_swap", src_comp=[-1, 1, 1], dest_comp=1) +intrinsic("deref_atomic_fadd", src_comp=[-1, 1], dest_comp=1) +intrinsic("deref_atomic_fmin", src_comp=[-1, 1], dest_comp=1) +intrinsic("deref_atomic_fmax", src_comp=[-1, 1], dest_comp=1) +intrinsic("deref_atomic_fcomp_swap", src_comp=[-1, 1, 1], dest_comp=1) # SSBO atomic intrinsics #