Add *some* type checking for assignments
This commit is contained in:
@@ -331,6 +331,45 @@ relational_result_type(const struct glsl_type *type_a,
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Validates that a value can be assigned to a location with a specified type
|
||||
*
|
||||
* Validates that \c rhs can be assigned to some location. If the types are
|
||||
* not an exact match but an automatic conversion is possible, \c rhs will be
|
||||
* converted.
|
||||
*
|
||||
* \return
|
||||
* \c NULL if \c rhs cannot be assigned to a location with type \c lhs_type.
|
||||
* Otherwise the actual RHS to be assigned will be returned. This may be
|
||||
* \c rhs, or it may be \c rhs after some type conversion.
|
||||
*
|
||||
* \note
|
||||
* In addition to being used for assignments, this function is used to
|
||||
* type-check return values.
|
||||
*/
|
||||
ir_instruction *
|
||||
validate_assignment(const glsl_type *lhs_type, ir_instruction *rhs)
|
||||
{
|
||||
const glsl_type *const rhs_type = rhs->type;
|
||||
|
||||
/* If there is already some error in the RHS, just return it. Anything
|
||||
* else will lead to an avalanche of error message back to the user.
|
||||
*/
|
||||
if (rhs_type->is_error())
|
||||
return rhs;
|
||||
|
||||
/* FINISHME: For GLSL 1.10, check that the types are not arrays. */
|
||||
|
||||
/* If the types are identical, the assignment can trivially proceed.
|
||||
*/
|
||||
if (rhs_type == lhs_type)
|
||||
return rhs;
|
||||
|
||||
/* FINISHME: Check for and apply automatic conversions. */
|
||||
return NULL;
|
||||
}
|
||||
|
||||
|
||||
ir_instruction *
|
||||
ast_node::hir(exec_list *instructions,
|
||||
struct _mesa_glsl_parse_state *state)
|
||||
@@ -448,8 +487,11 @@ ast_expression::hir(exec_list *instructions,
|
||||
}
|
||||
}
|
||||
|
||||
/* FINISHME: Check that the LHS and RHS have matching types. */
|
||||
/* FINISHME: For GLSL 1.10, check that the types are not arrays. */
|
||||
ir_instruction *rhs = validate_assignment(op[0]->type, op[1]);
|
||||
if (rhs == NULL) {
|
||||
type = glsl_error_type;
|
||||
rhs = op[1];
|
||||
}
|
||||
|
||||
ir_instruction *tmp = new ir_assignment(op[0], op[1], NULL);
|
||||
instructions->push_tail(tmp);
|
||||
|
Reference in New Issue
Block a user