From: Jakub Jelinek Date: Mon, 10 Nov 2014 23:08:08 +0000 (+0100) Subject: ipa-icf-gimple.c (func_checker::compare_bb): Fix comment typo. X-Git-Url: https://git.libre-soc.org/?a=commitdiff_plain;h=b607f49b020e547d0967029c6e39ef7c9b271470;p=gcc.git ipa-icf-gimple.c (func_checker::compare_bb): Fix comment typo. * ipa-icf-gimple.c (func_checker::compare_bb): Fix comment typo. (func_checker::compare_gimple_call): Compare gimple_call_fn, gimple_call_chain, gimple_call_fntype and call flags. testsuite/ * gcc.dg/ubsan/ipa-icf-1.c: New test. * gcc.dg/ipa/ipa-icf-31.c: New test. Co-Authored-By: Martin Liska From-SVN: r217323 --- diff --git a/gcc/ChangeLog b/gcc/ChangeLog index 63d43b68239..9d7dc265cb6 100644 --- a/gcc/ChangeLog +++ b/gcc/ChangeLog @@ -1,3 +1,10 @@ +2014-11-11 Jakub Jelinek + Martin Liska + + * ipa-icf-gimple.c (func_checker::compare_bb): Fix comment typo. + (func_checker::compare_gimple_call): Compare gimple_call_fn, + gimple_call_chain, gimple_call_fntype and call flags. + 2014-11-10 Vladimir Makarov PR rtl-optimization/63620 diff --git a/gcc/ipa-icf-gimple.c b/gcc/ipa-icf-gimple.c index 75b5cfbc202..a7e5a9241ab 100644 --- a/gcc/ipa-icf-gimple.c +++ b/gcc/ipa-icf-gimple.c @@ -554,7 +554,7 @@ func_checker::parse_labels (sem_bb *bb) In general, a collection of equivalence dictionaries is built for types like SSA names, declarations (VAR_DECL, PARM_DECL, ..). This infrastructure - is utilized by every statement-by-stament comparison function. */ + is utilized by every statement-by-statement comparison function. */ bool func_checker::compare_bb (sem_bb *bb1, sem_bb *bb2) @@ -659,12 +659,39 @@ func_checker::compare_gimple_call (gimple s1, gimple s2) if (gimple_call_num_args (s1) != gimple_call_num_args (s2)) return false; - t1 = gimple_call_fndecl (s1); - t2 = gimple_call_fndecl (s2); - - /* Function pointer variables are not supported yet. */ + t1 = gimple_call_fn (s1); + t2 = gimple_call_fn (s2); if (!compare_operand (t1, t2)) - return return_false(); + return return_false (); + + /* Compare flags. */ + if (gimple_call_internal_p (s1) != gimple_call_internal_p (s2) + || gimple_call_ctrl_altering_p (s1) != gimple_call_ctrl_altering_p (s2) + || gimple_call_tail_p (s1) != gimple_call_tail_p (s2) + || gimple_call_return_slot_opt_p (s1) != gimple_call_return_slot_opt_p (s2) + || gimple_call_from_thunk_p (s1) != gimple_call_from_thunk_p (s2) + || gimple_call_va_arg_pack_p (s1) != gimple_call_va_arg_pack_p (s2) + || gimple_call_alloca_for_var_p (s1) != gimple_call_alloca_for_var_p (s2) + || gimple_call_with_bounds_p (s1) != gimple_call_with_bounds_p (s2)) + return false; + + if (gimple_call_internal_p (s1) + && gimple_call_internal_fn (s1) != gimple_call_internal_fn (s2)) + return false; + + tree fntype1 = gimple_call_fntype (s1); + tree fntype2 = gimple_call_fntype (s2); + if ((fntype1 && !fntype2) + || (!fntype1 && fntype2) + || (fntype1 && !types_compatible_p (fntype1, fntype2))) + return return_false_with_msg ("call function types are not compatible"); + + tree chain1 = gimple_call_chain (s1); + tree chain2 = gimple_call_chain (s2); + if ((chain1 && !chain2) + || (!chain1 && chain2) + || !compare_operand (chain1, chain2)) + return return_false_with_msg ("static call chains are different"); /* Checking of argument. */ for (i = 0; i < gimple_call_num_args (s1); ++i) diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog index 812696db961..a44ae99c20e 100644 --- a/gcc/testsuite/ChangeLog +++ b/gcc/testsuite/ChangeLog @@ -1,3 +1,8 @@ +2014-11-11 Jakub Jelinek + + * gcc.dg/ubsan/ipa-icf-1.c: New test. + * gcc.dg/ipa/ipa-icf-31.c: New test. + 2014-11-10 Patrick Palka PR middle-end/63748 diff --git a/gcc/testsuite/gcc.dg/ipa/ipa-icf-31.c b/gcc/testsuite/gcc.dg/ipa/ipa-icf-31.c new file mode 100644 index 00000000000..6a5ec2efe86 --- /dev/null +++ b/gcc/testsuite/gcc.dg/ipa/ipa-icf-31.c @@ -0,0 +1,41 @@ +/* { dg-do run } */ +/* { dg-options "-O2 -fipa-icf" } */ + +__attribute__ ((noinline, noclone)) +int f1 (int x, int (*p1) (void), int (*p2) (void)) +{ + if (x) + return p1 (); + else + return p2 (); +} + +__attribute__ ((noinline, noclone)) +int f2 (int x, int (*p1) (void), int (*p2) (void)) +{ + if (x) + return p2 (); + else + return p1 (); +} + +__attribute__ ((noinline, noclone)) +int f3 (void) +{ + return 1; +} + +__attribute__ ((noinline, noclone)) +int f4 (void) +{ + return 2; +} + +int +main () +{ + if (f1 (0, f3, f4) != 2 || f1 (1, f3, f4) != 1 || f2 (0, f3, f4) != 1 + || f2 (1, f3, f4) != 2) + __builtin_abort (); + return 0; +} diff --git a/gcc/testsuite/gcc.dg/ubsan/ipa-icf-1.c b/gcc/testsuite/gcc.dg/ubsan/ipa-icf-1.c new file mode 100644 index 00000000000..1638ec45e37 --- /dev/null +++ b/gcc/testsuite/gcc.dg/ubsan/ipa-icf-1.c @@ -0,0 +1,23 @@ +/* { dg-do run } */ +/* { dg-skip-if "" { *-*-* } { "*" } { "-O2" } } */ +/* { dg-options "-fsanitize=undefined -fipa-icf" } */ + +__attribute__ ((noinline, noclone)) +int f1 (int x, int y) +{ + return x + y; +} + +__attribute__ ((noinline, noclone)) +int f2 (int x, int y) +{ + return x - y; +} + +int +main () +{ + if (f1 (5, 6) != 11 || f2 (5, 6) != -1) + __builtin_abort (); + return 0; +}