Add ir_variable::clone
[mesa.git] / ir.h
diff --git a/ir.h b/ir.h
index 3ef37083697fca2ad143c87052c197ce0100bad5..de6f09318adac56a20b9cff6325f916765cefba8 100644 (file)
--- a/ir.h
+++ b/ir.h
@@ -40,6 +40,7 @@ class ir_instruction : public exec_node {
 public:
    const struct glsl_type *type;
 
+   class ir_constant *constant_expression_value();
    virtual void accept(ir_visitor *) = 0;
 
    /**
@@ -109,6 +110,26 @@ public:
       v->visit(this);
    }
 
+   /**
+    * Duplicate an IR variable
+    *
+    * \note
+    * This will probably be made \c virtual and moved to the base class
+    * eventually.
+    */
+   ir_variable *clone() const
+   {
+      ir_variable *var = new ir_variable(type, name);
+
+      var->read_only = this->read_only;
+      var->centroid = this->centroid;
+      var->invariant = this->invariant;
+      var->mode = this->mode;
+      var->interpolation = this->interpolation;
+
+      return var;
+   }
+
    const char *name;
 
    unsigned read_only:1;
@@ -143,6 +164,11 @@ public:
       v->visit(this);
    }
 
+   /**
+    * Get the name of the function for which this is a signature
+    */
+   const char *function_name() const;
+
    /**
     * Function return type.
     *
@@ -159,6 +185,12 @@ public:
     * Pointer to the label that begins the function definition.
     */
    ir_label *definition;
+
+private:
+   /** Function of which this signature is one overload. */
+   class ir_function *function;
+
+   friend class ir_function;
 };
 
 
@@ -174,6 +206,20 @@ public:
       v->visit(this);
    }
 
+   void add_signature(ir_function_signature *sig)
+   {
+      sig->function = this;
+      signatures.push_tail(sig);
+   }
+
+   /**
+    * Get an iterator for the set of function signatures
+    */
+   exec_list_iterator iterator()
+   {
+      return signatures.iterator();
+   }
+
    /**
     * Find a signature that matches a set of actual parameters.
     */
@@ -184,14 +230,42 @@ public:
     */
    const char *name;
 
+private:
    /**
     * Set of overloaded functions with this name.
     */
    struct exec_list signatures;
 };
+
+inline const char *ir_function_signature::function_name() const
+{
+   return function->name;
+}
 /*@}*/
 
 
+/**
+ * IR instruction representing high-level if-statements
+ */
+class ir_if : public ir_instruction {
+public:
+   ir_if(ir_rvalue *condition)
+      : condition(condition)
+   {
+      /* empty */
+   }
+
+   virtual void accept(ir_visitor *v)
+   {
+      v->visit(this);
+   }
+
+   ir_rvalue *condition;
+   exec_list  then_instructions;
+   exec_list  else_instructions;
+};
+
+
 class ir_assignment : public ir_rvalue {
 public:
    ir_assignment(ir_rvalue *lhs, ir_rvalue *rhs, ir_rvalue *condition);
@@ -335,8 +409,7 @@ public:
     */
    const char *callee_name() const
    {
-      /* FINISHME: This only works for functions that have definitions. */
-      return callee->definition->label;
+      return callee->function_name();
    }
 
 private:
@@ -458,15 +531,12 @@ public:
 
    bool is_lvalue()
    {
-      ir_variable *as_var;
-
       if (var == NULL)
-        return NULL;
-
-      as_var = var->as_variable();
+        return false;
 
+      ir_variable *const as_var = var->as_variable();
       if (as_var == NULL)
-        return NULL;
+        return false;
 
       return !as_var->read_only;
    }