glsl: Prepare standalone compiler to be able to use parameter lists
[mesa.git] / src / compiler / glsl / builtin_functions.cpp
index edd02bb031b7a19abb978cc8982b52df7755c290..102c0398e6fc18b2944d237ec1e16951d4b0dafb 100644 (file)
@@ -244,6 +244,15 @@ gpu_shader5_es(const _mesa_glsl_parse_state *state)
           state->OES_gpu_shader5_enable;
 }
 
+static bool
+gpu_shader5_or_OES_texture_cube_map_array(const _mesa_glsl_parse_state *state)
+{
+   return state->is_version(400, 320) ||
+          state->ARB_gpu_shader5_enable ||
+          state->EXT_texture_cube_map_array_enable ||
+          state->OES_texture_cube_map_array_enable;
+}
+
 static bool
 es31_not_gs5(const _mesa_glsl_parse_state *state)
 {
@@ -264,6 +273,13 @@ shader_packing_or_es31_or_gpu_shader5(const _mesa_glsl_parse_state *state)
           state->is_version(400, 310);
 }
 
+static bool
+gpu_shader5_or_es31_or_integer_functions(const _mesa_glsl_parse_state *state)
+{
+   return gpu_shader5_or_es31(state) ||
+          state->MESA_shader_integer_functions_enable;
+}
+
 static bool
 fs_interpolate_at(const _mesa_glsl_parse_state *state)
 {
@@ -327,15 +343,13 @@ static bool
 fs_texture_cube_map_array(const _mesa_glsl_parse_state *state)
 {
    return state->stage == MESA_SHADER_FRAGMENT &&
-          (state->is_version(400, 0) ||
-           state->ARB_texture_cube_map_array_enable);
+          state->has_texture_cube_map_array();
 }
 
 static bool
 texture_cube_map_array(const _mesa_glsl_parse_state *state)
 {
-   return state->is_version(400, 0) ||
-          state->ARB_texture_cube_map_array_enable;
+   return state->has_texture_cube_map_array();
 }
 
 static bool
@@ -353,11 +367,13 @@ texture_query_lod(const _mesa_glsl_parse_state *state)
 }
 
 static bool
-texture_gather(const _mesa_glsl_parse_state *state)
+texture_gather_cube_map_array(const _mesa_glsl_parse_state *state)
 {
-   return state->is_version(400, 0) ||
+   return state->is_version(400, 320) ||
           state->ARB_texture_gather_enable ||
-          state->ARB_gpu_shader5_enable;
+          state->ARB_gpu_shader5_enable ||
+          state->EXT_texture_cube_map_array_enable ||
+          state->OES_texture_cube_map_array_enable;
 }
 
 static bool
@@ -528,6 +544,12 @@ barrier_supported(const _mesa_glsl_parse_state *state)
           state->stage == MESA_SHADER_TESS_CTRL;
 }
 
+static bool
+vote(const _mesa_glsl_parse_state *state)
+{
+   return state->ARB_shader_group_vote_enable;
+}
+
 /** @} */
 
 /******************************************************************************/
@@ -563,10 +585,6 @@ public:
 private:
    void *mem_ctx;
 
-   /** Global variables used by built-in functions. */
-   ir_variable *gl_ModelViewProjectionMatrix;
-   ir_variable *gl_Vertex;
-
    void create_shader();
    void create_intrinsics();
    void create_builtins();
@@ -853,6 +871,8 @@ private:
    ir_function_signature *_shader_clock(builtin_available_predicate avail,
                                         const glsl_type *type);
 
+   ir_function_signature *_vote(enum ir_expression_operation opcode);
+
 #undef B0
 #undef B1
 #undef B2
@@ -881,9 +901,7 @@ enum image_function_flags {
  *  @{
  */
 builtin_builder::builtin_builder()
-   : shader(NULL),
-     gl_ModelViewProjectionMatrix(NULL),
-     gl_Vertex(NULL)
+   : shader(NULL)
 {
    mem_ctx = NULL;
 }
@@ -948,18 +966,8 @@ builtin_builder::create_shader()
     * GLSL utility code that could be linked against any stage, so just
     * arbitrarily pick GL_VERTEX_SHADER.
     */
-   shader = _mesa_new_shader(NULL, 0, GL_VERTEX_SHADER);
+   shader = _mesa_new_shader(0, MESA_SHADER_VERTEX);
    shader->symbols = new(mem_ctx) glsl_symbol_table;
-
-   gl_ModelViewProjectionMatrix =
-      new(mem_ctx) ir_variable(glsl_type::mat4_type,
-                               "gl_ModelViewProjectionMatrix",
-                               ir_var_uniform);
-
-   shader->symbols->add_variable(gl_ModelViewProjectionMatrix);
-
-   gl_Vertex = in_var(glsl_type::vec4_type, "gl_Vertex");
-   shader->symbols->add_variable(gl_Vertex);
 }
 
 /** @} */
@@ -2541,9 +2549,9 @@ builtin_builder::create_builtins()
                 _texture(ir_tg4, texture_gather_or_es31, glsl_type::ivec4_type, glsl_type::isamplerCube_type, glsl_type::vec3_type),
                 _texture(ir_tg4, texture_gather_or_es31, glsl_type::uvec4_type, glsl_type::usamplerCube_type, glsl_type::vec3_type),
 
-                _texture(ir_tg4, texture_gather, glsl_type::vec4_type, glsl_type::samplerCubeArray_type, glsl_type::vec4_type),
-                _texture(ir_tg4, texture_gather, glsl_type::ivec4_type, glsl_type::isamplerCubeArray_type, glsl_type::vec4_type),
-                _texture(ir_tg4, texture_gather, glsl_type::uvec4_type, glsl_type::usamplerCubeArray_type, glsl_type::vec4_type),
+                _texture(ir_tg4, texture_gather_cube_map_array, glsl_type::vec4_type, glsl_type::samplerCubeArray_type, glsl_type::vec4_type),
+                _texture(ir_tg4, texture_gather_cube_map_array, glsl_type::ivec4_type, glsl_type::isamplerCubeArray_type, glsl_type::vec4_type),
+                _texture(ir_tg4, texture_gather_cube_map_array, glsl_type::uvec4_type, glsl_type::usamplerCubeArray_type, glsl_type::vec4_type),
 
                 _texture(ir_tg4, gpu_shader5_or_es31, glsl_type::vec4_type, glsl_type::sampler2D_type, glsl_type::vec2_type, TEX_COMPONENT),
                 _texture(ir_tg4, gpu_shader5_or_es31, glsl_type::ivec4_type, glsl_type::isampler2D_type, glsl_type::vec2_type, TEX_COMPONENT),
@@ -2561,14 +2569,14 @@ builtin_builder::create_builtins()
                 _texture(ir_tg4, gpu_shader5_or_es31, glsl_type::ivec4_type, glsl_type::isamplerCube_type, glsl_type::vec3_type, TEX_COMPONENT),
                 _texture(ir_tg4, gpu_shader5_or_es31, glsl_type::uvec4_type, glsl_type::usamplerCube_type, glsl_type::vec3_type, TEX_COMPONENT),
 
-                _texture(ir_tg4, gpu_shader5, glsl_type::vec4_type, glsl_type::samplerCubeArray_type, glsl_type::vec4_type, TEX_COMPONENT),
-                _texture(ir_tg4, gpu_shader5, glsl_type::ivec4_type, glsl_type::isamplerCubeArray_type, glsl_type::vec4_type, TEX_COMPONENT),
-                _texture(ir_tg4, gpu_shader5, glsl_type::uvec4_type, glsl_type::usamplerCubeArray_type, glsl_type::vec4_type, TEX_COMPONENT),
+                _texture(ir_tg4, gpu_shader5_or_OES_texture_cube_map_array, glsl_type::vec4_type, glsl_type::samplerCubeArray_type, glsl_type::vec4_type, TEX_COMPONENT),
+                _texture(ir_tg4, gpu_shader5_or_OES_texture_cube_map_array, glsl_type::ivec4_type, glsl_type::isamplerCubeArray_type, glsl_type::vec4_type, TEX_COMPONENT),
+                _texture(ir_tg4, gpu_shader5_or_OES_texture_cube_map_array, glsl_type::uvec4_type, glsl_type::usamplerCubeArray_type, glsl_type::vec4_type, TEX_COMPONENT),
 
                 _texture(ir_tg4, gpu_shader5_or_es31, glsl_type::vec4_type, glsl_type::sampler2DShadow_type, glsl_type::vec2_type),
                 _texture(ir_tg4, gpu_shader5_or_es31, glsl_type::vec4_type, glsl_type::sampler2DArrayShadow_type, glsl_type::vec3_type),
                 _texture(ir_tg4, gpu_shader5_or_es31, glsl_type::vec4_type, glsl_type::samplerCubeShadow_type, glsl_type::vec3_type),
-                _texture(ir_tg4, gpu_shader5, glsl_type::vec4_type, glsl_type::samplerCubeArrayShadow_type, glsl_type::vec4_type),
+                _texture(ir_tg4, gpu_shader5_or_OES_texture_cube_map_array, glsl_type::vec4_type, glsl_type::samplerCubeArrayShadow_type, glsl_type::vec4_type),
                 _texture(ir_tg4, gpu_shader5, glsl_type::vec4_type, glsl_type::sampler2DRectShadow_type, glsl_type::vec2_type),
                 NULL);
 
@@ -2935,6 +2943,10 @@ builtin_builder::create_builtins()
                               glsl_type::uvec2_type),
                 NULL);
 
+   add_function("anyInvocationARB", _vote(ir_unop_vote_any), NULL);
+   add_function("allInvocationsARB", _vote(ir_unop_vote_all), NULL);
+   add_function("allInvocationsEqualARB", _vote(ir_unop_vote_eq), NULL);
+
 #undef F
 #undef FI
 #undef FIUD
@@ -3950,15 +3962,9 @@ builtin_builder::_ftransform()
 {
    MAKE_SIG(glsl_type::vec4_type, compatibility_vs_only, 0);
 
-   body.emit(ret(new(mem_ctx) ir_expression(ir_binop_mul,
-      glsl_type::vec4_type,
-      var_ref(gl_ModelViewProjectionMatrix),
-      var_ref(gl_Vertex))));
-
-   /* FINISHME: Once the ir_expression() constructor handles type inference
-    *           for matrix operations, we can simplify this to:
-    *
-    *    body.emit(ret(mul(gl_ModelViewProjectionMatrix, gl_Vertex)));
+   /* ftransform() refers to global variables, and is always emitted
+    * directly by ast_function.cpp.  Just emit a prototype here so we
+    * can recognize calls to it.
     */
    return sig;
 }
@@ -4989,7 +4995,8 @@ builtin_builder::_bitfieldExtract(const glsl_type *type)
    ir_variable *value  = in_var(type, "value");
    ir_variable *offset = in_var(glsl_type::int_type, "offset");
    ir_variable *bits   = in_var(glsl_type::int_type, "bits");
-   MAKE_SIG(type, gpu_shader5_or_es31, 3, value, offset, bits);
+   MAKE_SIG(type, gpu_shader5_or_es31_or_integer_functions, 3, value, offset,
+            bits);
 
    operand cast_offset = is_uint ? i2u(offset) : operand(offset);
    operand cast_bits = is_uint ? i2u(bits) : operand(bits);
@@ -5009,7 +5016,8 @@ builtin_builder::_bitfieldInsert(const glsl_type *type)
    ir_variable *insert = in_var(type, "insert");
    ir_variable *offset = in_var(glsl_type::int_type, "offset");
    ir_variable *bits   = in_var(glsl_type::int_type, "bits");
-   MAKE_SIG(type, gpu_shader5_or_es31, 4, base, insert, offset, bits);
+   MAKE_SIG(type, gpu_shader5_or_es31_or_integer_functions, 4, base, insert,
+            offset, bits);
 
    operand cast_offset = is_uint ? i2u(offset) : operand(offset);
    operand cast_bits = is_uint ? i2u(bits) : operand(bits);
@@ -5021,26 +5029,26 @@ builtin_builder::_bitfieldInsert(const glsl_type *type)
    return sig;
 }
 
-UNOP(bitfieldReverse, ir_unop_bitfield_reverse, gpu_shader5_or_es31)
+UNOP(bitfieldReverse, ir_unop_bitfield_reverse, gpu_shader5_or_es31_or_integer_functions)
 
 ir_function_signature *
 builtin_builder::_bitCount(const glsl_type *type)
 {
-   return unop(gpu_shader5_or_es31, ir_unop_bit_count,
+   return unop(gpu_shader5_or_es31_or_integer_functions, ir_unop_bit_count,
                glsl_type::ivec(type->vector_elements), type);
 }
 
 ir_function_signature *
 builtin_builder::_findLSB(const glsl_type *type)
 {
-   return unop(gpu_shader5_or_es31, ir_unop_find_lsb,
+   return unop(gpu_shader5_or_es31_or_integer_functions, ir_unop_find_lsb,
                glsl_type::ivec(type->vector_elements), type);
 }
 
 ir_function_signature *
 builtin_builder::_findMSB(const glsl_type *type)
 {
-   return unop(gpu_shader5_or_es31, ir_unop_find_msb,
+   return unop(gpu_shader5_or_es31_or_integer_functions, ir_unop_find_msb,
                glsl_type::ivec(type->vector_elements), type);
 }
 
@@ -5060,7 +5068,7 @@ builtin_builder::_fma(builtin_available_predicate avail, const glsl_type *type)
 ir_function_signature *
 builtin_builder::_ldexp(const glsl_type *x_type, const glsl_type *exp_type)
 {
-   return binop(x_type->base_type == GLSL_TYPE_DOUBLE ? fp64 : gpu_shader5_or_es31,
+   return binop(x_type->base_type == GLSL_TYPE_DOUBLE ? fp64 : gpu_shader5_or_es31_or_integer_functions,
                 ir_binop_ldexp, x_type, x_type, exp_type);
 }
 
@@ -5082,7 +5090,7 @@ builtin_builder::_frexp(const glsl_type *x_type, const glsl_type *exp_type)
 {
    ir_variable *x = in_var(x_type, "x");
    ir_variable *exponent = out_var(exp_type, "exp");
-   MAKE_SIG(x_type, gpu_shader5_or_es31, 2, x, exponent);
+   MAKE_SIG(x_type, gpu_shader5_or_es31_or_integer_functions, 2, x, exponent);
 
    const unsigned vec_elem = x_type->vector_elements;
    const glsl_type *bvec = glsl_type::get_instance(GLSL_TYPE_BOOL, vec_elem, 1);
@@ -5131,7 +5139,7 @@ builtin_builder::_uaddCarry(const glsl_type *type)
    ir_variable *x = in_var(type, "x");
    ir_variable *y = in_var(type, "y");
    ir_variable *carry = out_var(type, "carry");
-   MAKE_SIG(type, gpu_shader5_or_es31, 3, x, y, carry);
+   MAKE_SIG(type, gpu_shader5_or_es31_or_integer_functions, 3, x, y, carry);
 
    body.emit(assign(carry, ir_builder::carry(x, y)));
    body.emit(ret(add(x, y)));
@@ -5145,7 +5153,7 @@ builtin_builder::_usubBorrow(const glsl_type *type)
    ir_variable *x = in_var(type, "x");
    ir_variable *y = in_var(type, "y");
    ir_variable *borrow = out_var(type, "borrow");
-   MAKE_SIG(type, gpu_shader5_or_es31, 3, x, y, borrow);
+   MAKE_SIG(type, gpu_shader5_or_es31_or_integer_functions, 3, x, y, borrow);
 
    body.emit(assign(borrow, ir_builder::borrow(x, y)));
    body.emit(ret(sub(x, y)));
@@ -5163,7 +5171,7 @@ builtin_builder::_mulExtended(const glsl_type *type)
    ir_variable *y = in_var(type, "y");
    ir_variable *msb = out_var(type, "msb");
    ir_variable *lsb = out_var(type, "lsb");
-   MAKE_SIG(glsl_type::void_type, gpu_shader5_or_es31, 4, x, y, msb, lsb);
+   MAKE_SIG(glsl_type::void_type, gpu_shader5_or_es31_or_integer_functions, 4, x, y, msb, lsb);
 
    body.emit(assign(msb, imul_high(x, y)));
    body.emit(assign(lsb, mul(x, y)));
@@ -5576,6 +5584,16 @@ builtin_builder::_shader_clock(builtin_available_predicate avail,
    return sig;
 }
 
+ir_function_signature *
+builtin_builder::_vote(enum ir_expression_operation opcode)
+{
+   ir_variable *value = in_var(glsl_type::bool_type, "value");
+
+   MAKE_SIG(glsl_type::bool_type, vote, 1, value);
+   body.emit(ret(expr(opcode, value)));
+   return sig;
+}
+
 /** @} */
 
 /******************************************************************************/
@@ -5636,9 +5654,9 @@ _mesa_glsl_get_builtin_function_shader()
  * Get the function signature for main from a shader
  */
 ir_function_signature *
-_mesa_get_main_function_signature(gl_shader *sh)
+_mesa_get_main_function_signature(glsl_symbol_table *symbols)
 {
-   ir_function *const f = sh->symbols->get_function("main");
+   ir_function *const f = symbols->get_function("main");
    if (f != NULL) {
       exec_list void_parameters;