summaryrefslogtreecommitdiffstats
path: root/src/glsl/ir.h
diff options
context:
space:
mode:
authorIan Romanick <[email protected]>2010-08-02 18:48:25 -0700
committerIan Romanick <[email protected]>2010-08-04 16:47:27 -0700
commit5a7758efbe14dee026245a4f4f4fb3ccf7b2c23b (patch)
treebe214c6f3ea4be5ec4472afa5b3426d5191380f5 /src/glsl/ir.h
parent8e9ce2eb56a087c2544112700ae1abe3f96648dd (diff)
glsl2: Add ir_assignment::write_mask and associated methods
Replace swizzles on the LHS with additional swizzles on the RHS and a write mask in the assignment instruction. As part of this add ir_assignment::set_lhs. Ideally we'd make ir_assignment::lhs private to prevent erroneous writes, but that would require a lot of code butchery at this point. Add ir_assignment constructor that takes an explicit write mask. This is required for ir_assignment::clone, but it can also be used in other places. Without this, ir_assignment clones lose their write masks, and incorrect IR is generated in optimization passes. Add ir_assignment::whole_variable_written method. This method gets the variable on the LHS if the whole variable is written or NULL otherwise. This is different from ir->lhs->whole_variable_referenced() because the latter has no knowledge of the write mask stored in the ir_assignment. Gut all code from ir_to_mesa that handled swizzles on the LHS of assignments. There is probably some other refactoring that could be done here, but that can be left for another day.
Diffstat (limited to 'src/glsl/ir.h')
-rw-r--r--src/glsl/ir.h44
1 files changed, 43 insertions, 1 deletions
diff --git a/src/glsl/ir.h b/src/glsl/ir.h
index f964b36083a..98789503e06 100644
--- a/src/glsl/ir.h
+++ b/src/glsl/ir.h
@@ -514,6 +514,16 @@ class ir_assignment : public ir_instruction {
public:
ir_assignment(ir_rvalue *lhs, ir_rvalue *rhs, ir_rvalue *condition);
+ /**
+ * Construct an assignment with an explicit write mask
+ *
+ * \note
+ * Since a write mask is supplied, the LHS must already be a bare
+ * \c ir_dereference. The cannot be any swizzles in the LHS.
+ */
+ ir_assignment(ir_dereference *lhs, ir_rvalue *rhs, ir_rvalue *condition,
+ unsigned write_mask);
+
virtual ir_assignment *clone(void *mem_ctx, struct hash_table *ht) const;
virtual ir_constant *constant_expression_value();
@@ -531,9 +541,31 @@ public:
}
/**
+ * Get a whole variable written by an assignment
+ *
+ * If the LHS of the assignment writes a whole variable, the variable is
+ * returned. Otherwise \c NULL is returned. Examples of whole-variable
+ * assignment are:
+ *
+ * - Assigning to a scalar
+ * - Assigning to all components of a vector
+ * - Whole array (or matrix) assignment
+ * - Whole structure assignment
+ */
+ ir_variable *whole_variable_written();
+
+ /**
+ * Set the LHS of an assignment
+ */
+ void set_lhs(ir_rvalue *lhs);
+
+ /**
* Left-hand side of the assignment.
+ *
+ * This should be treated as read only. If you need to set the LHS of an
+ * assignment, use \c ir_assignment::set_lhs.
*/
- ir_rvalue *lhs;
+ ir_dereference *lhs;
/**
* Value being assigned
@@ -544,6 +576,16 @@ public:
* Optional condition for the assignment.
*/
ir_rvalue *condition;
+
+
+ /**
+ * Component mask written
+ *
+ * For non-vector types in the LHS, this field will be zero. For vector
+ * types, a bit will be set for each component that is written. Note that
+ * for \c vec2 and \c vec3 types only the lower bits will ever be set.
+ */
+ unsigned write_mask:4;
};
/* Update ir_expression::num_operands() and operator_strs when