Hello,this patch makes gimple checking of vector comparisons more strict by ensuring that it doesn't return a boolean. It also fixes a bug that this check detected in fold-const.c: for (void)(x<0), the C front-end was calling fold_unary_loc on the conversion to void, which was then converted to if(x<0)(void)0.
2012-11-02 Marc Glisse <marc.gli...@inria.fr> * tree-cfg.c (verify_gimple_comparison): Verify that vector comparison returns a vector. * fold-const.c (fold_unary_loc): Disable conversion optimization for void type. -- Marc Glisse
Index: gcc/fold-const.c =================================================================== --- gcc/fold-const.c (revision 193060) +++ gcc/fold-const.c (working copy) @@ -7742,21 +7742,22 @@ fold_unary_loc (location_t loc, enum tre /* If we have (type) (a CMP b) and type is an integral type, return new expression involving the new type. Canonicalize (type) (a CMP b) to (a CMP b) ? (type) true : (type) false for non-integral type. Do not fold the result as that would not simplify further, also folding again results in recursions. */ if (TREE_CODE (type) == BOOLEAN_TYPE) return build2_loc (loc, TREE_CODE (op0), type, TREE_OPERAND (op0, 0), TREE_OPERAND (op0, 1)); - else if (!INTEGRAL_TYPE_P (type) && TREE_CODE (type) != VECTOR_TYPE) + else if (!INTEGRAL_TYPE_P (type) && !VOID_TYPE_P (type) + && TREE_CODE (type) != VECTOR_TYPE) return build3_loc (loc, COND_EXPR, type, op0, constant_boolean_node (true, type), constant_boolean_node (false, type)); } /* Handle cases of two conversions in a row. */ if (CONVERT_EXPR_P (op0)) { tree inside_type = TREE_TYPE (TREE_OPERAND (op0, 0)); tree inter_type = TREE_TYPE (op0); Index: gcc/tree-cfg.c =================================================================== --- gcc/tree-cfg.c (revision 193060) +++ gcc/tree-cfg.c (working copy) @@ -3263,21 +3263,30 @@ verify_gimple_comparison (tree type, tre error ("mismatching comparison operand types"); debug_generic_expr (op0_type); debug_generic_expr (op1_type); return true; } /* The resulting type of a comparison may be an effective boolean type. */ if (INTEGRAL_TYPE_P (type) && (TREE_CODE (type) == BOOLEAN_TYPE || TYPE_PRECISION (type) == 1)) - ; + { + if (TREE_CODE (op0_type) == VECTOR_TYPE + || TREE_CODE (op1_type) == VECTOR_TYPE) + { + error ("vector comparison returning a boolean"); + debug_generic_expr (op0_type); + debug_generic_expr (op1_type); + return true; + } + } /* Or an integer vector type with the same size and element count as the comparison operand types. */ else if (TREE_CODE (type) == VECTOR_TYPE && TREE_CODE (TREE_TYPE (type)) == INTEGER_TYPE) { if (TREE_CODE (op0_type) != VECTOR_TYPE || TREE_CODE (op1_type) != VECTOR_TYPE) { error ("non-vector operands in vector comparison"); debug_generic_expr (op0_type);