ralloc: a new MIT-licensed recursive memory allocator.
[mesa.git] / src / glsl / ast.h
index adb5fb11d471c495645336f441b09ef0152c8f93..878f48b20706613373c7959c998c499559ecf616 100644 (file)
 #include "list.h"
 #include "glsl_parser_extras.h"
 
-struct ir_instruction;
 struct _mesa_glsl_parse_state;
 
 struct YYLTYPE;
 
+/**
+ * \defgroup AST Abstract syntax tree node definitions
+ *
+ * An abstract syntax tree is generated by the parser.  This is a fairly
+ * direct representation of the gramma derivation for the source program.
+ * No symantic checking is done during the generation of the AST.  Only
+ * syntactic checking is done.  Symantic checking is performed by a later
+ * stage that converts the AST to a more generic intermediate representation.
+ *
+ *@{
+ */
+/**
+ * Base class of all abstract syntax tree nodes
+ */
 class ast_node {
 public:
-   /* Callers of this talloc-based new need not call delete. It's
-    * easier to just talloc_free 'ctx' (or any of its ancestors). */
+   /* Callers of this ralloc-based new need not call delete. It's
+    * easier to just ralloc_free 'ctx' (or any of its ancestors). */
    static void* operator new(size_t size, void *ctx)
    {
       void *node;
 
-      node = talloc_size(ctx, size);
+      node = rzalloc_size(ctx, size);
       assert(node != NULL);
 
       return node;
    }
 
    /* If the user *does* call delete, that's OK, we will just
-    * talloc_free in that case. */
+    * ralloc_free in that case. */
    static void operator delete(void *table)
    {
-      talloc_free(table);
+      ralloc_free(table);
    }
 
+   /**
+    * Print an AST node in something approximating the original GLSL code
+    */
    virtual void print(void) const;
+
+   /**
+    * Convert the AST node to the high-level intermediate representation
+    */
    virtual ir_rvalue *hir(exec_list *instructions,
                          struct _mesa_glsl_parse_state *state);
 
@@ -92,19 +112,29 @@ public:
       this->location.column = locp.first_column;
    }
 
+   /**
+    * Source location of the AST node.
+    */
    struct {
-      unsigned source;
-      unsigned line;
-      unsigned column;
+      unsigned source;    /**< GLSL source number. */
+      unsigned line;      /**< Line number within the source string. */
+      unsigned column;    /**< Column in the line. */
    } location;
 
    exec_node link;
 
 protected:
+   /**
+    * The only constructor is protected so that only derived class objects can
+    * be created.
+    */
    ast_node(void);
 };
 
 
+/**
+ * Operators for AST expression nodes.
+ */
 enum ast_operators {
    ast_assign,
    ast_plus,        /**< Unary + operator. */
@@ -162,6 +192,9 @@ enum ast_operators {
    ast_sequence
 };
 
+/**
+ * Representation of any sort of expression.
+ */
 class ast_expression : public ast_node {
 public:
    ast_expression(int oper, ast_expression *,
@@ -285,23 +318,78 @@ public:
 
 
 enum {
-   ast_precision_high = 0, /**< Default precision. */
+   ast_precision_none = 0, /**< Absence of precision qualifier. */
+   ast_precision_high,
    ast_precision_medium,
    ast_precision_low
 };
 
 struct ast_type_qualifier {
-   unsigned invariant:1;
-   unsigned constant:1;
-   unsigned attribute:1;
-   unsigned varying:1;
-   unsigned in:1;
-   unsigned out:1;
-   unsigned centroid:1;
-   unsigned uniform:1;
-   unsigned smooth:1;
-   unsigned flat:1;
-   unsigned noperspective:1;
+   union {
+      struct {
+        unsigned invariant:1;
+        unsigned constant:1;
+        unsigned attribute:1;
+        unsigned varying:1;
+        unsigned in:1;
+        unsigned out:1;
+        unsigned centroid:1;
+        unsigned uniform:1;
+        unsigned smooth:1;
+        unsigned flat:1;
+        unsigned noperspective:1;
+
+        /** \name Layout qualifiers for GL_ARB_fragment_coord_conventions */
+        /*@{*/
+        unsigned origin_upper_left:1;
+        unsigned pixel_center_integer:1;
+        /*@}*/
+
+        /**
+         * Flag set if GL_ARB_explicit_attrib_location "location" layout
+         * qualifier is used.
+         */
+        unsigned explicit_location:1;
+
+         /** \name Layout qualifiers for GL_AMD_conservative_depth */
+         /** \{ */
+         unsigned depth_any:1;
+         unsigned depth_greater:1;
+         unsigned depth_less:1;
+         unsigned depth_unchanged:1;
+         /** \} */
+      }
+      /** \brief Set of flags, accessed by name. */
+      q;
+
+      /** \brief Set of flags, accessed as a bitmask. */
+      unsigned i;
+   } flags;
+
+   /**
+    * Location specified via GL_ARB_explicit_attrib_location layout
+    *
+    * \note
+    * This field is only valid if \c explicit_location is set.
+    */
+   unsigned location;
+
+   /**
+    * Return true if and only if an interpolation qualifier is present.
+    */
+   bool has_interpolation() const;
+
+   /**
+    * \brief Return string representation of interpolation qualifier.
+    *
+    * If an interpolation qualifier is present, then return that qualifier's
+    * string representation. Otherwise, return null. For example, if the
+    * noperspective bit is set, then this returns "noperspective".
+    *
+    * If multiple interpolation qualifiers are somehow present, then the
+    * returned string is undefined but not null.
+    */
+   const char *interpolation_string() const;
 };
 
 class ast_struct_specifier : public ast_node {
@@ -382,7 +470,8 @@ public:
    /** Construct a type specifier from a type name */
    ast_type_specifier(const char *name) 
       : type_specifier(ast_type_name), type_name(name), structure(NULL),
-       is_array(false), array_size(NULL), precision(ast_precision_high)
+       is_array(false), array_size(NULL), precision(ast_precision_none),
+       is_precision_statement(false)
    {
       /* empty */
    }
@@ -390,7 +479,8 @@ public:
    /** Construct a type specifier from a structure definition */
    ast_type_specifier(ast_struct_specifier *s)
       : type_specifier(ast_struct), type_name(s->name), structure(s),
-       is_array(false), array_size(NULL), precision(ast_precision_high)
+       is_array(false), array_size(NULL), precision(ast_precision_none),
+       is_precision_statement(false)
    {
       /* empty */
    }
@@ -412,6 +502,8 @@ public:
    ast_expression *array_size;
 
    unsigned precision:2;
+
+   bool is_precision_statement;
 };
 
 
@@ -449,6 +541,13 @@ public:
 
 class ast_parameter_declarator : public ast_node {
 public:
+   ast_parameter_declarator()
+   {
+      this->identifier = NULL;
+      this->is_array = false;
+      this->array_size = 0;
+   }
+
    virtual void print(void) const;
 
    virtual ir_rvalue *hir(exec_list *instructions,
@@ -515,25 +614,6 @@ private:
 };
 
 
-class ast_declaration_statement : public ast_node {
-public:
-   ast_declaration_statement(void);
-
-   enum {
-      ast_function,
-      ast_declaration,
-      ast_precision
-   } mode;
-
-   union {
-      class ast_function *function;
-      ast_declarator_list *declarator;
-      ast_type_specifier *type;
-      ast_node *node;
-   } declaration;
-};
-
-
 class ast_expression_statement : public ast_node {
 public:
    ast_expression_statement(ast_expression *);
@@ -639,14 +719,18 @@ public:
    ast_function *prototype;
    ast_compound_statement *body;
 };
-
+/*@}*/
 
 extern void
 _mesa_ast_to_hir(exec_list *instructions, struct _mesa_glsl_parse_state *state);
 
-extern struct ir_rvalue *
-_mesa_ast_field_selection_to_hir(const struct ast_expression *expr,
+extern ir_rvalue *
+_mesa_ast_field_selection_to_hir(const ast_expression *expr,
                                 exec_list *instructions,
                                 struct _mesa_glsl_parse_state *state);
 
+void
+emit_function(_mesa_glsl_parse_state *state, exec_list *instructions,
+             ir_function *f);
+
 #endif /* AST_H */