This is the mail archive of the
gcc-patches@gcc.gnu.org
mailing list for the GCC project.
Re: [PATCH] Various middle-end type fixes
On Thu, 11 Sep 2008, Paolo Bonzini wrote:
> Richard Guenther wrote:
> > I'm nearly through bootstrapping with type and gimple-checking enabled
> > from verify_stmts ...
>
> Would it be acceptable in stage3 to apply the more strict type-checking
> rules to TRUTH_*_EXPRs too?
This is what I have in the pipeline currently, do you think of more
than the
case TRUTH_AND_EXPR:
case TRUTH_OR_EXPR:
case TRUTH_XOR_EXPR:
{
/* We allow any kind of integral typed argument and result. */
if (!INTEGRAL_TYPE_P (rhs1_type)
|| !INTEGRAL_TYPE_P (rhs2_type)
|| !INTEGRAL_TYPE_P (lhs_type))
{
error ("type mismatch in binary truth expression");
debug_generic_expr (lhs_type);
debug_generic_expr (rhs1_type);
debug_generic_expr (rhs2_type);
return true;
}
?
Richard.
2008-09-11 Richard Guenther <rguenther@suse.de>
* tree-cfg.c (verify_types_in_gimple_assign): Rename to ...
(verify_gimple_assign): ... this. Split into ...
(verify_gimple_assign_unary): ... this,
(verify_gimple_assign_binary): ... that,
(verify_gimple_assign_single): ... and this.
(verify_types_in_gimple_stmt): Call verify_gimple_assign.
Fix GIMPLE_CHANGE_DYNAMIC_TYPE handling.
(verify_types_in_gimple_min_lval): Handle TARGET_MEM_REF.
(verify_types_in_gimple_reference): Be forgiving with
VIEW_CONVERT_EXPRs.
(verify_gimple_phi): Deal with virtual operands.
* tree.def (PREDICT_EXPR): Change to tcc_expression.
Index: trunk/gcc/tree-cfg.c
===================================================================
*** trunk.orig/gcc/tree-cfg.c
--- trunk/gcc/tree-cfg.c
*************** verify_types_in_gimple_min_lval (tree ex
*** 3035,3048 ****
if (is_gimple_id (expr))
return false;
! if (TREE_CODE (expr) != INDIRECT_REF
! && TREE_CODE (expr) != ALIGN_INDIRECT_REF
! && TREE_CODE (expr) != MISALIGNED_INDIRECT_REF)
{
error ("invalid expression for min lvalue");
return true;
}
op = TREE_OPERAND (expr, 0);
if (!is_gimple_val (op))
{
--- 3035,3051 ----
if (is_gimple_id (expr))
return false;
! if (!INDIRECT_REF_P (expr)
! && TREE_CODE (expr) != TARGET_MEM_REF)
{
error ("invalid expression for min lvalue");
return true;
}
+ /* TARGET_MEM_REFs are strange beasts. */
+ if (TREE_CODE (expr) == TARGET_MEM_REF)
+ return false;
+
op = TREE_OPERAND (expr, 0);
if (!is_gimple_val (op))
{
*************** verify_types_in_gimple_reference (tree e
*** 3131,3136 ****
--- 3134,3142 ----
/* For VIEW_CONVERT_EXPRs which are allowed here, too, there
is nothing to verify. Gross mismatches at most invoke
undefined behavior. */
+ if (TREE_CODE (expr) == VIEW_CONVERT_EXPR
+ && !handled_component_p (op))
+ return false;
expr = op;
}
*************** verify_gimple_comparison (tree type, tre
*** 3257,3301 ****
return false;
}
! /* Verify the contents of a GIMPLE_ASSIGN STMT. Returns true when there
! is a problem, otherwise false.
!
! Verify that the types of the LHS and the RHS operands are
! compatible. This verification largely depends on what kind of
! operation is done on the RHS of the assignment. It is not always
! the case that all the types of the operands must match (e.g., 'a =
! (unsigned long) b' or 'ptr = ptr + 1'). */
static bool
! verify_types_in_gimple_assign (gimple stmt)
{
enum tree_code rhs_code = gimple_assign_rhs_code (stmt);
tree lhs = gimple_assign_lhs (stmt);
- tree rhs1 = gimple_assign_rhs1 (stmt);
- tree rhs2 = (gimple_num_ops (stmt) == 3) ? gimple_assign_rhs2 (stmt) : NULL;
tree lhs_type = TREE_TYPE (lhs);
tree rhs1_type = TREE_TYPE (rhs1);
- tree rhs2_type = (rhs2) ? TREE_TYPE (rhs2) : NULL;
! /* Special codes we cannot handle via their class. */
switch (rhs_code)
{
CASE_CONVERT:
{
- if (!is_gimple_val (rhs1))
- {
- error ("invalid operand in conversion");
- return true;
- }
-
/* Allow conversions between integral types and pointers only if
! there is no sign or zero extension involved. */
! if (((POINTER_TYPE_P (lhs_type) && INTEGRAL_TYPE_P (rhs1_type))
! || (POINTER_TYPE_P (rhs1_type) && INTEGRAL_TYPE_P (lhs_type)))
! && (TYPE_PRECISION (lhs_type) == TYPE_PRECISION (rhs1_type)
! /* For targets were the precision of sizetype doesn't
! match that of pointers we need the following. */
! || lhs_type == sizetype || rhs1_type == sizetype))
return false;
/* Allow conversion from integer to offset type and vice versa. */
--- 3263,3312 ----
return false;
}
! /* Verify a gimple assignment statement STMT with an unary rhs.
! Returns true if anything is wrong. */
static bool
! verify_gimple_assign_unary (gimple stmt)
{
enum tree_code rhs_code = gimple_assign_rhs_code (stmt);
tree lhs = gimple_assign_lhs (stmt);
tree lhs_type = TREE_TYPE (lhs);
+ tree rhs1 = gimple_assign_rhs1 (stmt);
tree rhs1_type = TREE_TYPE (rhs1);
! if (!is_gimple_reg (lhs)
! && !(optimize == 0
! && TREE_CODE (lhs_type) == COMPLEX_TYPE))
! {
! error ("non-register as LHS of unary operation");
! return true;
! }
!
! if (!is_gimple_val (rhs1))
! {
! error ("invalid operand in unary operation");
! return true;
! }
!
! /* First handle conversions. */
switch (rhs_code)
{
CASE_CONVERT:
{
/* Allow conversions between integral types and pointers only if
! there is no sign or zero extension involved.
! For targets were the precision of sizetype doesn't match that
! of pointers we need to allow arbitrary conversions from and
! to sizetype. */
! if ((POINTER_TYPE_P (lhs_type)
! && INTEGRAL_TYPE_P (rhs1_type)
! && (TYPE_PRECISION (lhs_type) >= TYPE_PRECISION (rhs1_type)
! || rhs1_type == sizetype))
! || (POINTER_TYPE_P (rhs1_type)
! && INTEGRAL_TYPE_P (lhs_type)
! && (TYPE_PRECISION (rhs1_type) >= TYPE_PRECISION (lhs_type)
! || lhs_type == sizetype)))
return false;
/* Allow conversion from integer to offset type and vice versa. */
*************** verify_types_in_gimple_assign (gimple st
*** 3320,3331 ****
case FIXED_CONVERT_EXPR:
{
- if (!is_gimple_val (rhs1))
- {
- error ("invalid operand in conversion");
- return true;
- }
-
if (!valid_fixed_convert_types_p (lhs_type, rhs1_type)
&& !valid_fixed_convert_types_p (rhs1_type, lhs_type))
{
--- 3331,3336 ----
*************** verify_types_in_gimple_assign (gimple st
*** 3340,3351 ****
case FLOAT_EXPR:
{
- if (!is_gimple_val (rhs1))
- {
- error ("invalid operand in int to float conversion");
- return true;
- }
-
if (!INTEGRAL_TYPE_P (rhs1_type) || !SCALAR_FLOAT_TYPE_P (lhs_type))
{
error ("invalid types in conversion to floating point");
--- 3345,3350 ----
*************** verify_types_in_gimple_assign (gimple st
*** 3359,3370 ****
case FIX_TRUNC_EXPR:
{
- if (!is_gimple_val (rhs1))
- {
- error ("invalid operand in float to int conversion");
- return true;
- }
-
if (!INTEGRAL_TYPE_P (lhs_type) || !SCALAR_FLOAT_TYPE_P (rhs1_type))
{
error ("invalid types in conversion to integer");
--- 3358,3363 ----
*************** verify_types_in_gimple_assign (gimple st
*** 3376,3393 ****
return false;
}
! case COMPLEX_EXPR:
{
! if (!is_gimple_val (rhs1) || !is_gimple_val (rhs2))
! {
! error ("invalid operands in complex expression");
! return true;
! }
! if (!TREE_CODE (lhs_type) == COMPLEX_TYPE
! || !(TREE_CODE (rhs1_type) == INTEGER_TYPE
|| SCALAR_FLOAT_TYPE_P (rhs1_type))
! || !(TREE_CODE (rhs2_type) == INTEGER_TYPE
|| SCALAR_FLOAT_TYPE_P (rhs2_type)))
{
error ("type mismatch in complex expression");
--- 3369,3447 ----
return false;
}
! case TRUTH_NOT_EXPR:
{
! }
!
! case NEGATE_EXPR:
! case ABS_EXPR:
! case BIT_NOT_EXPR:
! case PAREN_EXPR:
! case NON_LVALUE_EXPR:
! case CONJ_EXPR:
! case REDUC_MAX_EXPR:
! case REDUC_MIN_EXPR:
! case REDUC_PLUS_EXPR:
! case VEC_UNPACK_HI_EXPR:
! case VEC_UNPACK_LO_EXPR:
! case VEC_UNPACK_FLOAT_HI_EXPR:
! case VEC_UNPACK_FLOAT_LO_EXPR:
! break;
!
! default:
! gcc_unreachable ();
! }
! /* For the remaining codes assert there is no conversion involved. */
! if (!useless_type_conversion_p (lhs_type, rhs1_type))
! {
! error ("non-trivial conversion in unary operation");
! debug_generic_expr (lhs_type);
! debug_generic_expr (rhs1_type);
! return true;
! }
!
! return false;
! }
!
! /* Verify a gimple assignment statement STMT with a binary rhs.
! Returns true if anything is wrong. */
!
! static bool
! verify_gimple_assign_binary (gimple stmt)
! {
! enum tree_code rhs_code = gimple_assign_rhs_code (stmt);
! tree lhs = gimple_assign_lhs (stmt);
! tree lhs_type = TREE_TYPE (lhs);
! tree rhs1 = gimple_assign_rhs1 (stmt);
! tree rhs1_type = TREE_TYPE (rhs1);
! tree rhs2 = gimple_assign_rhs2 (stmt);
! tree rhs2_type = TREE_TYPE (rhs2);
!
! if (!is_gimple_reg (lhs)
! && !(optimize == 0
! && TREE_CODE (lhs_type) == COMPLEX_TYPE))
! {
! error ("non-register as LHS of binary operation");
! return true;
! }
!
! if (!is_gimple_val (rhs1)
! || !is_gimple_val (rhs2))
! {
! error ("invalid operands in binary operation");
! return true;
! }
!
! /* First handle operations that involve different types. */
! switch (rhs_code)
! {
! case COMPLEX_EXPR:
! {
! if (TREE_CODE (lhs_type) != COMPLEX_TYPE
! || !(INTEGRAL_TYPE_P (rhs1_type)
|| SCALAR_FLOAT_TYPE_P (rhs1_type))
! || !(INTEGRAL_TYPE_P (rhs2_type)
|| SCALAR_FLOAT_TYPE_P (rhs2_type)))
{
error ("type mismatch in complex expression");
*************** verify_types_in_gimple_assign (gimple st
*** 3400,3425 ****
return false;
}
- case CONSTRUCTOR:
- {
- /* In this context we know that we are on the RHS of an
- assignment, so CONSTRUCTOR operands are OK. */
- /* FIXME: verify constructor arguments. */
- return false;
- }
-
case LSHIFT_EXPR:
case RSHIFT_EXPR:
case LROTATE_EXPR:
case RROTATE_EXPR:
{
! if (!is_gimple_val (rhs1) || !is_gimple_val (rhs2))
! {
! error ("invalid operands in shift expression");
! return true;
! }
!
! if (!TREE_CODE (rhs1_type) == INTEGER_TYPE
|| !useless_type_conversion_p (lhs_type, rhs1_type))
{
error ("type mismatch in shift expression");
--- 3454,3466 ----
return false;
}
case LSHIFT_EXPR:
case RSHIFT_EXPR:
case LROTATE_EXPR:
case RROTATE_EXPR:
{
! if (!INTEGRAL_TYPE_P (rhs1_type)
! || !INTEGRAL_TYPE_P (rhs2_type)
|| !useless_type_conversion_p (lhs_type, rhs1_type))
{
error ("type mismatch in shift expression");
*************** verify_types_in_gimple_assign (gimple st
*** 3432,3459 ****
return false;
}
! case PLUS_EXPR:
! case MINUS_EXPR:
{
! if (POINTER_TYPE_P (lhs_type)
! || POINTER_TYPE_P (rhs1_type)
! || POINTER_TYPE_P (rhs2_type))
{
! error ("invalid (pointer) operands to plus/minus");
return true;
}
! /* Continue with generic binary expression handling. */
! break;
}
case POINTER_PLUS_EXPR:
{
- if (!is_gimple_val (rhs1) || !is_gimple_val (rhs2))
- {
- error ("invalid operands in pointer plus expression");
- return true;
- }
if (!POINTER_TYPE_P (rhs1_type)
|| !useless_type_conversion_p (lhs_type, rhs1_type)
|| !useless_type_conversion_p (sizetype, rhs2_type))
--- 3473,3500 ----
return false;
}
! case VEC_LSHIFT_EXPR:
! case VEC_RSHIFT_EXPR:
{
! if (TREE_CODE (rhs1_type) != VECTOR_TYPE
! || !INTEGRAL_TYPE_P (TREE_TYPE (rhs1_type))
! || (!INTEGRAL_TYPE_P (rhs2_type)
! && (TREE_CODE (rhs2_type) != VECTOR_TYPE
! || !INTEGRAL_TYPE_P (TREE_TYPE (rhs2_type))))
! || !useless_type_conversion_p (lhs_type, rhs1_type))
{
! error ("type mismatch in vector shift expression");
! debug_generic_expr (lhs_type);
! debug_generic_expr (rhs1_type);
! debug_generic_expr (rhs2_type);
return true;
}
! return false;
}
case POINTER_PLUS_EXPR:
{
if (!POINTER_TYPE_P (rhs1_type)
|| !useless_type_conversion_p (lhs_type, rhs1_type)
|| !useless_type_conversion_p (sizetype, rhs2_type))
*************** verify_types_in_gimple_assign (gimple st
*** 3468,3497 ****
return false;
}
- case ADDR_EXPR:
- {
- tree op = TREE_OPERAND (rhs1, 0);
- if (!is_gimple_addressable (op))
- {
- error ("invalid operand in unary expression");
- return true;
- }
-
- if (!one_pointer_to_useless_type_conversion_p (lhs_type, TREE_TYPE (op))
- /* FIXME: a longstanding wart, &a == &a[0]. */
- && (TREE_CODE (TREE_TYPE (op)) != ARRAY_TYPE
- || !one_pointer_to_useless_type_conversion_p (lhs_type,
- TREE_TYPE (TREE_TYPE (op)))))
- {
- error ("type mismatch in address expression");
- debug_generic_stmt (lhs_type);
- debug_generic_stmt (TYPE_POINTER_TO (TREE_TYPE (op)));
- return true;
- }
-
- return verify_types_in_gimple_reference (TREE_OPERAND (rhs1, 0));
- }
-
case TRUTH_ANDIF_EXPR:
case TRUTH_ORIF_EXPR:
gcc_unreachable ();
--- 3509,3514 ----
*************** verify_types_in_gimple_assign (gimple st
*** 3500,3511 ****
case TRUTH_OR_EXPR:
case TRUTH_XOR_EXPR:
{
- if (!is_gimple_val (rhs1) || !is_gimple_val (rhs2))
- {
- error ("invalid operands in truth expression");
- return true;
- }
-
/* We allow any kind of integral typed argument and result. */
if (!INTEGRAL_TYPE_P (rhs1_type)
|| !INTEGRAL_TYPE_P (rhs2_type)
--- 3517,3522 ----
*************** verify_types_in_gimple_assign (gimple st
*** 3521,3628 ****
return false;
}
! case TRUTH_NOT_EXPR:
! {
! if (!is_gimple_val (rhs1))
! {
! error ("invalid operand in unary not");
! return true;
! }
! /* For TRUTH_NOT_EXPR we can have any kind of integral
! typed arguments and results. */
! if (!INTEGRAL_TYPE_P (rhs1_type)
! || !INTEGRAL_TYPE_P (lhs_type))
{
! error ("type mismatch in not expression");
! debug_generic_expr (lhs_type);
! debug_generic_expr (rhs1_type);
return true;
}
! return false;
}
! /* After gimplification we should not have any of these. */
! case ASM_EXPR:
! case BIND_EXPR:
! case CALL_EXPR:
! case COND_EXPR:
! case TREE_LIST:
! case COMPOUND_EXPR:
! case MODIFY_EXPR:
! case INIT_EXPR:
! case GOTO_EXPR:
! case LABEL_EXPR:
! case RETURN_EXPR:
! case TRY_FINALLY_EXPR:
! case TRY_CATCH_EXPR:
! case EH_FILTER_EXPR:
! case STATEMENT_LIST:
! {
! error ("tree node that should already be gimple.");
! return true;
! }
! case OBJ_TYPE_REF:
! /* FIXME. */
! return false;
! default:;
}
! /* Generic handling via classes. */
! switch (TREE_CODE_CLASS (rhs_code))
{
! case tcc_exceptional: /* for SSA_NAME */
! case tcc_unary:
! if (!useless_type_conversion_p (lhs_type, rhs1_type))
! {
! error ("non-trivial conversion at assignment");
! debug_generic_expr (lhs_type);
! debug_generic_expr (rhs1_type);
! return true;
! }
! break;
! case tcc_binary:
! if (!is_gimple_val (rhs1) || !is_gimple_val (rhs2))
! {
! error ("invalid operands in binary expression");
! return true;
! }
! if (!useless_type_conversion_p (lhs_type, rhs1_type)
! || !useless_type_conversion_p (lhs_type, rhs2_type))
! {
! error ("type mismatch in binary expression");
! debug_generic_stmt (lhs_type);
! debug_generic_stmt (rhs1_type);
! debug_generic_stmt (rhs2_type);
return true;
}
! break;
! case tcc_reference:
! /* All tcc_reference trees are GIMPLE_SINGLE_RHS. Verify that
! no implicit type change happens here. */
! if (!useless_type_conversion_p (lhs_type, rhs1_type))
! {
! error ("non-trivial conversion at assignment");
! debug_generic_expr (lhs_type);
! debug_generic_expr (rhs1_type);
return true;
}
! return verify_types_in_gimple_reference (rhs1);
! case tcc_comparison:
! return verify_gimple_comparison (lhs_type, rhs1, rhs2);
default:;
}
! return false;
}
/* Verify the contents of a GIMPLE_RETURN STMT. Returns true when there
is a problem, otherwise false. */
--- 3532,3757 ----
return false;
}
! case LT_EXPR:
! case LE_EXPR:
! case GT_EXPR:
! case GE_EXPR:
! case EQ_EXPR:
! case NE_EXPR:
! case UNORDERED_EXPR:
! case ORDERED_EXPR:
! case UNLT_EXPR:
! case UNLE_EXPR:
! case UNGT_EXPR:
! case UNGE_EXPR:
! case UNEQ_EXPR:
! case LTGT_EXPR:
! /* Comparisons are also binary, but the result type is not
! connected to the operand types. */
! return verify_gimple_comparison (lhs_type, rhs1, rhs2);
! case PLUS_EXPR:
! case MINUS_EXPR:
! {
! if (POINTER_TYPE_P (lhs_type)
! || POINTER_TYPE_P (rhs1_type)
! || POINTER_TYPE_P (rhs2_type))
{
! error ("invalid (pointer) operands to plus/minus");
return true;
}
! /* Continue with generic binary expression handling. */
! break;
}
! case MULT_EXPR:
! case TRUNC_DIV_EXPR:
! case CEIL_DIV_EXPR:
! case FLOOR_DIV_EXPR:
! case ROUND_DIV_EXPR:
! case TRUNC_MOD_EXPR:
! case CEIL_MOD_EXPR:
! case FLOOR_MOD_EXPR:
! case ROUND_MOD_EXPR:
! case RDIV_EXPR:
! case EXACT_DIV_EXPR:
! case MIN_EXPR:
! case MAX_EXPR:
! case BIT_IOR_EXPR:
! case BIT_XOR_EXPR:
! case BIT_AND_EXPR:
! case WIDEN_SUM_EXPR:
! case WIDEN_MULT_EXPR:
! case VEC_WIDEN_MULT_HI_EXPR:
! case VEC_WIDEN_MULT_LO_EXPR:
! case VEC_PACK_TRUNC_EXPR:
! case VEC_PACK_SAT_EXPR:
! case VEC_PACK_FIX_TRUNC_EXPR:
! case VEC_EXTRACT_EVEN_EXPR:
! case VEC_EXTRACT_ODD_EXPR:
! case VEC_INTERLEAVE_HIGH_EXPR:
! case VEC_INTERLEAVE_LOW_EXPR:
! /* Continue with generic binary expression handling. */
! break;
! default:
! gcc_unreachable ();
! }
! if (!useless_type_conversion_p (lhs_type, rhs1_type)
! || !useless_type_conversion_p (lhs_type, rhs2_type))
! {
! error ("type mismatch in binary expression");
! debug_generic_stmt (lhs_type);
! debug_generic_stmt (rhs1_type);
! debug_generic_stmt (rhs2_type);
! return true;
}
! return false;
! }
!
! /* Verify a gimple assignment statement STMT with a single rhs.
! Returns true if anything is wrong. */
!
! static bool
! verify_gimple_assign_single (gimple stmt)
! {
! enum tree_code rhs_code = gimple_assign_rhs_code (stmt);
! tree lhs = gimple_assign_lhs (stmt);
! tree lhs_type = TREE_TYPE (lhs);
! tree rhs1 = gimple_assign_rhs1 (stmt);
! tree rhs1_type = TREE_TYPE (rhs1);
! bool res = false;
!
! if (!useless_type_conversion_p (lhs_type, rhs1_type))
{
! error ("non-trivial conversion at assignment");
! debug_generic_expr (lhs_type);
! debug_generic_expr (rhs1_type);
! return true;
! }
! if (handled_component_p (lhs))
! res |= verify_types_in_gimple_reference (lhs);
!
! /* Special codes we cannot handle via their class. */
! switch (rhs_code)
! {
! case ADDR_EXPR:
! {
! tree op = TREE_OPERAND (rhs1, 0);
! if (!is_gimple_addressable (op))
! {
! error ("invalid operand in unary expression");
! return true;
! }
!
! if (!one_pointer_to_useless_type_conversion_p (lhs_type, TREE_TYPE (op))
! /* FIXME: a longstanding wart, &a == &a[0]. */
! && (TREE_CODE (TREE_TYPE (op)) != ARRAY_TYPE
! || !one_pointer_to_useless_type_conversion_p (lhs_type,
! TREE_TYPE (TREE_TYPE (op)))))
! {
! error ("type mismatch in address expression");
! debug_generic_stmt (lhs_type);
! debug_generic_stmt (TYPE_POINTER_TO (TREE_TYPE (op)));
! return true;
! }
!
! return verify_types_in_gimple_reference (op);
! }
!
! /* tcc_reference */
! case COMPONENT_REF:
! case BIT_FIELD_REF:
! case INDIRECT_REF:
! case ALIGN_INDIRECT_REF:
! case MISALIGNED_INDIRECT_REF:
! case ARRAY_REF:
! case ARRAY_RANGE_REF:
! case VIEW_CONVERT_EXPR:
! case REALPART_EXPR:
! case IMAGPART_EXPR:
! case TARGET_MEM_REF:
! if (!is_gimple_reg (lhs)
! && is_gimple_reg_type (TREE_TYPE (lhs)))
! {
! error ("invalid rhs for gimple memory store");
! debug_generic_stmt (lhs);
! debug_generic_stmt (rhs1);
return true;
}
! return res || verify_types_in_gimple_reference (rhs1);
! /* tcc_constant */
! case SSA_NAME:
! case INTEGER_CST:
! case REAL_CST:
! case FIXED_CST:
! case COMPLEX_CST:
! case VECTOR_CST:
! case STRING_CST:
! return res;
!
! /* tcc_declaration */
! case CONST_DECL:
! return res;
! case VAR_DECL:
! case PARM_DECL:
! if (!is_gimple_reg (lhs)
! && !is_gimple_reg (rhs1)
! && is_gimple_reg_type (TREE_TYPE (lhs)))
! {
! error ("invalid rhs for gimple memory store");
! debug_generic_stmt (lhs);
! debug_generic_stmt (rhs1);
return true;
}
! return res;
! case COND_EXPR:
! case CONSTRUCTOR:
! case OBJ_TYPE_REF:
! case ASSERT_EXPR:
! case WITH_SIZE_EXPR:
! case EXC_PTR_EXPR:
! case FILTER_EXPR:
! case POLYNOMIAL_CHREC:
! case DOT_PROD_EXPR:
! case VEC_COND_EXPR:
! case REALIGN_LOAD_EXPR:
! /* FIXME. */
! return res;
default:;
}
! return res;
}
+ /* Verify the contents of a GIMPLE_ASSIGN STMT. Returns true when there
+ is a problem, otherwise false. */
+
+ static bool
+ verify_gimple_assign (gimple stmt)
+ {
+ switch (gimple_assign_rhs_class (stmt))
+ {
+ case GIMPLE_SINGLE_RHS:
+ return verify_gimple_assign_single (stmt);
+
+ case GIMPLE_UNARY_RHS:
+ return verify_gimple_assign_unary (stmt);
+
+ case GIMPLE_BINARY_RHS:
+ return verify_gimple_assign_binary (stmt);
+
+ default:
+ gcc_unreachable ();
+ }
+ }
/* Verify the contents of a GIMPLE_RETURN STMT. Returns true when there
is a problem, otherwise false. */
*************** verify_gimple_phi (gimple stmt)
*** 3719,3725 ****
for (i = 0; i < gimple_phi_num_args (stmt); i++)
{
tree arg = gimple_phi_arg_def (stmt, i);
! if (!is_gimple_val (arg))
{
error ("Invalid PHI argument");
debug_generic_stmt (arg);
--- 3848,3857 ----
for (i = 0; i < gimple_phi_num_args (stmt); i++)
{
tree arg = gimple_phi_arg_def (stmt, i);
! if ((is_gimple_reg (gimple_phi_result (stmt))
! && !is_gimple_val (arg))
! || (!is_gimple_reg (gimple_phi_result (stmt))
! && !is_gimple_addressable (arg)))
{
error ("Invalid PHI argument");
debug_generic_stmt (arg);
*************** verify_types_in_gimple_stmt (gimple stmt
*** 3758,3764 ****
switch (gimple_code (stmt))
{
case GIMPLE_ASSIGN:
! return verify_types_in_gimple_assign (stmt);
case GIMPLE_LABEL:
return TREE_CODE (gimple_label_label (stmt)) != LABEL_DECL;
--- 3890,3896 ----
switch (gimple_code (stmt))
{
case GIMPLE_ASSIGN:
! return verify_gimple_assign (stmt);
case GIMPLE_LABEL:
return TREE_CODE (gimple_label_label (stmt)) != LABEL_DECL;
*************** verify_types_in_gimple_stmt (gimple stmt
*** 3784,3790 ****
return false;
case GIMPLE_CHANGE_DYNAMIC_TYPE:
! return (!is_gimple_reg (gimple_cdt_location (stmt))
|| !POINTER_TYPE_P (TREE_TYPE (gimple_cdt_location (stmt))));
case GIMPLE_PHI:
--- 3916,3922 ----
return false;
case GIMPLE_CHANGE_DYNAMIC_TYPE:
! return (!is_gimple_val (gimple_cdt_location (stmt))
|| !POINTER_TYPE_P (TREE_TYPE (gimple_cdt_location (stmt))));
case GIMPLE_PHI:
Index: trunk/gcc/tree.def
===================================================================
*** trunk.orig/gcc/tree.def
--- trunk/gcc/tree.def
*************** DEFTREECODE (VEC_INTERLEAVE_LOW_EXPR, "v
*** 1137,1143 ****
outcome (0 for not taken and 1 for taken). Once the profile is guessed
all conditional branches leading to execution paths executing the
PREDICT_EXPR will get predicted by the specified predictor. */
! DEFTREECODE (PREDICT_EXPR, "predict_expr", tcc_unary, 1)
/* OPTIMIZATION_NODE. Node to store the optimization options. */
DEFTREECODE (OPTIMIZATION_NODE, "optimization_node", tcc_exceptional, 0)
--- 1137,1143 ----
outcome (0 for not taken and 1 for taken). Once the profile is guessed
all conditional branches leading to execution paths executing the
PREDICT_EXPR will get predicted by the specified predictor. */
! DEFTREECODE (PREDICT_EXPR, "predict_expr", tcc_expression, 1)
/* OPTIMIZATION_NODE. Node to store the optimization options. */
DEFTREECODE (OPTIMIZATION_NODE, "optimization_node", tcc_exceptional, 0)