Hi,
The following test-case ICE's with -fgimple:
int __GIMPLE foo(int a)
{
int t1;
t1_1 = __builtin_abs (a);
return t1_1;
}
gimplefe-2.c:4:3: internal compiler error: in get_callee_fndecl, at tree.c:9500
t1_1 = __builtin_abs (a);
^~~~
0xe96e8d get_callee_fndecl(tree_node const*)
../../gcc/gcc/tree.c:9500
0x924d75 gimple_build_call_from_tree(tree_node*)
../../gcc/gcc/gimple.c:351
0x6c86b3 c_parser_gimple_statement
../../gcc/gcc/c/gimple-parser.c:393
0x6c86b3 c_parser_gimple_compound_statement
../../gcc/gcc/c/gimple-parser.c:216
0x6c86b3 c_parser_parse_gimple_body(c_parser*)
../../gcc/gcc/c/gimple-parser.c:93
0x6b04f1 c_parser_declaration_or_fndef
../../gcc/gcc/c/c-parser.c:2081
0x6b883b c_parser_external_declaration
../../gcc/gcc/c/c-parser.c:1464
0x6b92a1 c_parser_translation_unit
../../gcc/gcc/c/c-parser.c:1344
0x6b92a1 c_parse_file()
../../gcc/gcc/c/c-parser.c:18141
0x717832 c_common_parse_file()
../../gcc/gcc/c-family/c-opts.c:1102
This happens because __builtin_abs(a) gets folded to <nop_expr<abs_expr<a>>
and get_callee_fndecl expects CALL_EXPR.
The attached patch tries to fix the issue by building gimple_assign
with appropriate subcode
for functions that get folded to expression instead of trying to build
it as a function-call.
Is it OK to commit after bootstrap+test ?
Thanks,
Prathamesh
2017-02-04 Prathamesh Kulkarni <[email protected]>
* gimple-pretty-print.c (dump_unary_rhs): Change dump format for
ABS_EXPR for gimple dump.
* tree-pretty-print.c (dump_generic_node): Likewise.
c/
* gimple-parser.c (c_parser_gimple_statement): Check if rhs.value is
CALL_EXPR and build gimple_assign if it isn't.
testsuite/
* gcc.dg/gimplefe-23.c: New test-case.
diff --git a/gcc/c/gimple-parser.c b/gcc/c/gimple-parser.c
index 7feb6d0..4e2ae37 100644
--- a/gcc/c/gimple-parser.c
+++ b/gcc/c/gimple-parser.c
@@ -401,10 +401,22 @@ c_parser_gimple_statement (c_parser *parser, gimple_seq
*seq)
rhs = c_parser_gimple_unary_expression (parser);
if (rhs.value != error_mark_node)
{
- gimple *call = gimple_build_call_from_tree (rhs.value);
- gimple_call_set_lhs (call, lhs.value);
- gimple_seq_add_stmt (seq, call);
- gimple_set_location (call, loc);
+ if (TREE_CODE (rhs.value) == CALL_EXPR)
+ {
+ gimple *call = gimple_build_call_from_tree (rhs.value);
+ gimple_call_set_lhs (call, lhs.value);
+ gimple_seq_add_stmt (seq, call);
+ gimple_set_location (call, loc);
+ }
+ else
+ {
+ tree value = tree_strip_nop_conversions (rhs.value);
+ gcc_assert (get_gimple_rhs_class (TREE_CODE (value))
+ != GIMPLE_INVALID_RHS);
+ gassign *assign = gimple_build_assign (lhs.value, value);
+ gimple_seq_add_stmt (seq, assign);
+ gimple_set_location (assign, loc);
+ }
}
return;
}
diff --git a/gcc/gimple-pretty-print.c b/gcc/gimple-pretty-print.c
index 91c839d..f773d85 100644
--- a/gcc/gimple-pretty-print.c
+++ b/gcc/gimple-pretty-print.c
@@ -323,9 +323,18 @@ dump_unary_rhs (pretty_printer *buffer, gassign *gs, int
spc, int flags)
break;
case ABS_EXPR:
- pp_string (buffer, "ABS_EXPR <");
- dump_generic_node (buffer, rhs, spc, flags, false);
- pp_greater (buffer);
+ if (flags & TDF_GIMPLE)
+ {
+ pp_string (buffer, "__builtin_abs (");
+ dump_generic_node (buffer, rhs, spc, flags, false);
+ pp_right_paren (buffer);
+ }
+ else
+ {
+ pp_string (buffer, "ABS_EXPR <");
+ dump_generic_node (buffer, rhs, spc, flags, false);
+ pp_greater (buffer);
+ }
break;
default:
diff --git a/gcc/testsuite/gcc.dg/gimplefe-23.c
b/gcc/testsuite/gcc.dg/gimplefe-23.c
new file mode 100644
index 0000000..1448030
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/gimplefe-23.c
@@ -0,0 +1,11 @@
+/* { dg-do compile } */
+/* { dg-options "-O -fgimple -fdump-tree-ssa-gimple" } */
+
+int __GIMPLE foo(int a)
+{
+ int t1;
+ t1_1 = __builtin_abs (a);
+ return t1_1;
+}
+
+/* { dg-final { scan-tree-dump "__builtin_abs" "ssa" } } */
diff --git a/gcc/tree-pretty-print.c b/gcc/tree-pretty-print.c
index d823c2e..f1a5bdd 100644
--- a/gcc/tree-pretty-print.c
+++ b/gcc/tree-pretty-print.c
@@ -2441,9 +2441,18 @@ dump_generic_node (pretty_printer *pp, tree node, int
spc, int flags,
break;
case ABS_EXPR:
- pp_string (pp, "ABS_EXPR <");
- dump_generic_node (pp, TREE_OPERAND (node, 0), spc, flags, false);
- pp_greater (pp);
+ if (flags & TDF_GIMPLE)
+ {
+ pp_string (pp, "__builtin_abs (");
+ dump_generic_node (pp, TREE_OPERAND (node, 0), spc, flags, false);
+ pp_right_paren (pp);
+ }
+ else
+ {
+ pp_string (pp, "ABS_EXPR <");
+ dump_generic_node (pp, TREE_OPERAND (node, 0), spc, flags, false);
+ pp_greater (pp);
+ }
break;
case RANGE_EXPR: