summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--src/glsl/ir.cpp8
-rw-r--r--src/glsl/ir.h14
-rw-r--r--src/glsl/ir_clone.cpp1
-rw-r--r--src/glsl/ir_reader.cpp13
4 files changed, 30 insertions, 6 deletions
diff --git a/src/glsl/ir.cpp b/src/glsl/ir.cpp
index c6d96d8da03..ea018eb2d9e 100644
--- a/src/glsl/ir.cpp
+++ b/src/glsl/ir.cpp
@@ -1579,11 +1579,13 @@ ir_variable::determine_interpolation_mode(bool flat_shade)
}
-ir_function_signature::ir_function_signature(const glsl_type *return_type)
- : return_type(return_type), is_defined(false), _function(NULL)
+ir_function_signature::ir_function_signature(const glsl_type *return_type,
+ builtin_available_predicate b)
+ : return_type(return_type), is_defined(false), builtin_info(b),
+ _function(NULL)
{
this->ir_type = ir_type_function_signature;
- this->is_builtin = false;
+ this->is_builtin = builtin_info != NULL;
this->origin = NULL;
}
diff --git a/src/glsl/ir.h b/src/glsl/ir.h
index b45e6cbd831..d785259cc86 100644
--- a/src/glsl/ir.h
+++ b/src/glsl/ir.h
@@ -591,6 +591,11 @@ public:
const glsl_type *interface_type;
};
+/**
+ * A function that returns whether a built-in function is available in the
+ * current shading language (based on version, ES or desktop, and extensions).
+ */
+typedef bool (*builtin_available_predicate)(const _mesa_glsl_parse_state *);
/*@{*/
/**
@@ -602,7 +607,8 @@ class ir_function_signature : public ir_instruction {
* an ir_function.
*/
public:
- ir_function_signature(const glsl_type *return_type);
+ ir_function_signature(const glsl_type *return_type,
+ builtin_available_predicate builtin_info = NULL);
virtual ir_function_signature *clone(void *mem_ctx,
struct hash_table *ht) const;
@@ -684,6 +690,12 @@ public:
struct exec_list body;
private:
+ /**
+ * A function pointer to a predicate that answers whether a built-in
+ * function is available in the current shader. NULL if not a built-in.
+ */
+ builtin_available_predicate builtin_info;
+
/** Function of which this signature is one overload. */
class ir_function *_function;
diff --git a/src/glsl/ir_clone.cpp b/src/glsl/ir_clone.cpp
index a75b3b7622b..52e2fb54e41 100644
--- a/src/glsl/ir_clone.cpp
+++ b/src/glsl/ir_clone.cpp
@@ -330,6 +330,7 @@ ir_function_signature::clone_prototype(void *mem_ctx, struct hash_table *ht) con
copy->is_defined = false;
copy->is_builtin = this->is_builtin;
+ copy->builtin_info = this->builtin_info;
copy->origin = this;
/* Clone the parameter list, but NOT the body.
diff --git a/src/glsl/ir_reader.cpp b/src/glsl/ir_reader.cpp
index f263fe81096..8261d9f43f6 100644
--- a/src/glsl/ir_reader.cpp
+++ b/src/glsl/ir_reader.cpp
@@ -211,6 +211,12 @@ ir_reader::read_function(s_expression *expr, bool skip_body)
return added ? f : NULL;
}
+static bool
+always_available(const _mesa_glsl_parse_state *)
+{
+ return true;
+}
+
void
ir_reader::read_function_sig(ir_function *f, s_expression *expr, bool skip_body)
{
@@ -251,8 +257,11 @@ ir_reader::read_function_sig(ir_function *f, s_expression *expr, bool skip_body)
ir_function_signature *sig = f->exact_matching_signature(&hir_parameters);
if (sig == NULL && skip_body) {
/* If scanning for prototypes, generate a new signature. */
- sig = new(mem_ctx) ir_function_signature(return_type);
- sig->is_builtin = true;
+ /* ir_reader doesn't know what languages support a given built-in, so
+ * just say that they're always available. For now, other mechanisms
+ * guarantee the right built-ins are available.
+ */
+ sig = new(mem_ctx) ir_function_signature(return_type, always_available);
f->add_signature(sig);
} else if (sig != NULL) {
const char *badvar = sig->qualifiers_match(&hir_parameters);