spirv: handle AMD_gcn_shader extended instructions
[mesa.git] / src / compiler / spirv / vtn_private.h
index 7cb69d784305e496c44f5f2bda95a6784d9e995f..a8fa612384f9762d779bb152709d900ea84bb817 100644 (file)
@@ -274,8 +274,8 @@ struct vtn_type {
 
    const struct glsl_type *type;
 
-   /* The value that declares this type.  Used for finding decorations */
-   struct vtn_value *val;
+   /* The SPIR-V id of the given type. */
+   uint32_t id;
 
    /* Specifies the length of complex types.
     *
@@ -365,6 +365,9 @@ struct vtn_type {
    };
 };
 
+bool vtn_types_compatible(struct vtn_builder *b,
+                          struct vtn_type *t1, struct vtn_type *t2);
+
 struct vtn_variable;
 
 enum vtn_access_mode {
@@ -531,6 +534,7 @@ struct vtn_builder {
    jmp_buf fail_jump;
 
    const uint32_t *spirv;
+   size_t spirv_word_count;
 
    nir_shader *shader;
    const struct spirv_to_nir_options *options;
@@ -584,15 +588,25 @@ struct vtn_pointer *
 vtn_pointer_from_ssa(struct vtn_builder *b, nir_ssa_def *ssa,
                      struct vtn_type *ptr_type);
 
+static inline struct vtn_value *
+vtn_untyped_value(struct vtn_builder *b, uint32_t value_id)
+{
+   vtn_fail_if(value_id >= b->value_id_bound,
+               "SPIR-V id %u is out-of-bounds", value_id);
+   return &b->values[value_id];
+}
+
 static inline struct vtn_value *
 vtn_push_value(struct vtn_builder *b, uint32_t value_id,
                enum vtn_value_type value_type)
 {
-   assert(value_id < b->value_id_bound);
-   assert(b->values[value_id].value_type == vtn_value_type_invalid);
+   struct vtn_value *val = vtn_untyped_value(b, value_id);
 
-   b->values[value_id].value_type = value_type;
+   vtn_fail_if(val->value_type != vtn_value_type_invalid,
+               "SPIR-V id %u has already been written by another instruction",
+               value_id);
 
+   val->value_type = value_type;
    return &b->values[value_id];
 }
 
@@ -611,19 +625,13 @@ vtn_push_ssa(struct vtn_builder *b, uint32_t value_id,
    return val;
 }
 
-static inline struct vtn_value *
-vtn_untyped_value(struct vtn_builder *b, uint32_t value_id)
-{
-   assert(value_id < b->value_id_bound);
-   return &b->values[value_id];
-}
-
 static inline struct vtn_value *
 vtn_value(struct vtn_builder *b, uint32_t value_id,
           enum vtn_value_type value_type)
 {
    struct vtn_value *val = vtn_untyped_value(b, value_id);
-   assert(val->value_type == value_type);
+   vtn_fail_if(val->value_type != value_type,
+               "SPIR-V id %u is the wrong kind of value", value_id);
    return val;
 }
 
@@ -631,6 +639,12 @@ bool
 vtn_set_instruction_result_type(struct vtn_builder *b, SpvOp opcode,
                                 const uint32_t *w, unsigned count);
 
+static inline nir_constant *
+vtn_constant_value(struct vtn_builder *b, uint32_t value_id)
+{
+   return vtn_value(b, value_id, vtn_value_type_constant)->constant;
+}
+
 struct vtn_ssa_value *vtn_ssa_value(struct vtn_builder *b, uint32_t value_id);
 
 struct vtn_ssa_value *vtn_create_ssa_value(struct vtn_builder *b,
@@ -699,6 +713,9 @@ nir_op vtn_nir_alu_op_for_spirv_opcode(struct vtn_builder *b,
 void vtn_handle_alu(struct vtn_builder *b, SpvOp opcode,
                     const uint32_t *w, unsigned count);
 
+void vtn_handle_subgroup(struct vtn_builder *b, SpvOp opcode,
+                         const uint32_t *w, unsigned count);
+
 bool vtn_handle_glsl450_instruction(struct vtn_builder *b, uint32_t ext_opcode,
                                     const uint32_t *words, unsigned count);
 
@@ -715,4 +732,7 @@ vtn_u64_literal(const uint32_t *w)
    return (uint64_t)w[1] << 32 | w[0];
 }
 
+bool vtn_handle_amd_gcn_shader_instruction(struct vtn_builder *b, uint32_t ext_opcode,
+                                           const uint32_t *words, unsigned count);
+
 #endif /* _VTN_PRIVATE_H_ */