From: Robert Suchanek <[email protected]>
--param early-inlining-insns-cold=NUMBER
--param max-inline-insns-small-and-cold=NUMBER
Analysis shows that the main difference between -O2 and -Os goes down to
inlining of cold or unlikely functions. The new parameters (defaulted to
0) mean to disable these limitations with -Os. NUMBER could be set to
something like 4-32 to see the impact.
The main reason that smaller functions are treated as cold or unlikely
is the function cgraph_maybe_hot_edge_p () always returning FALSE for
-Os.
gcc/
* ipa-inline.cc (want_early_inline_function_p): Check if the
growth is greater than param_early_inlining_insns_cold.
(want_inline_small_function_p): Check if the growth is greater
than param_max_inline_insns_small_and_cold.
* params.opt (early-inlining-insns-cold): New option.
(max-inline-insns-small-and-cold): Likewise.
gcc/testsuite/
* gcc.dg/inline-cold-1.c: New test.
* gcc.dg/inline-cold-2.c: New test.
* gcc.dg/ipa/inline-cold-1.c: New test.
* gcc.dg/ipa/inline-cold-2.c: New test.
Cherry-picked c38d7e548cbb3defb141efb528cb356333e8eb7a
from https://github.com/MIPS/gcc
Signed-off-by: Robert Suchanek <[email protected]>
Signed-off-by: Faraz Shahbazker <[email protected]>
Signed-off-by: Aleksandar Rakic <[email protected]>
Signed-off-by: Eldar Osmanovic <[email protected]>
---
gcc/ipa-inline.cc | 4 +++-
gcc/params.opt | 8 ++++++++
gcc/testsuite/gcc.dg/inline-cold-1.c | 21 +++++++++++++++++++++
gcc/testsuite/gcc.dg/inline-cold-2.c | 21 +++++++++++++++++++++
gcc/testsuite/gcc.dg/ipa/inline-cold-1.c | 21 +++++++++++++++++++++
gcc/testsuite/gcc.dg/ipa/inline-cold-2.c | 21 +++++++++++++++++++++
6 files changed, 95 insertions(+), 1 deletion(-)
create mode 100644 gcc/testsuite/gcc.dg/inline-cold-1.c
create mode 100644 gcc/testsuite/gcc.dg/inline-cold-2.c
create mode 100644 gcc/testsuite/gcc.dg/ipa/inline-cold-1.c
create mode 100644 gcc/testsuite/gcc.dg/ipa/inline-cold-2.c
diff --git a/gcc/ipa-inline.cc b/gcc/ipa-inline.cc
index 5a7615666cc..928c2bb3f92 100644
--- a/gcc/ipa-inline.cc
+++ b/gcc/ipa-inline.cc
@@ -819,7 +819,8 @@ want_early_inline_function_p (struct cgraph_edge *e)
if (!want_inline || growth <= param_max_inline_insns_size)
;
- else if (!e->maybe_hot_p ())
+ else if (!e->maybe_hot_p ()
+ && growth > param_early_inlining_insns_cold)
{
if (dump_enabled_p ())
dump_printf_loc (MSG_MISSED_OPTIMIZATION, e->call_stmt,
@@ -1082,6 +1083,7 @@ want_inline_small_function_p (struct cgraph_edge *e, bool
report)
}
/* If call is cold, do not inline when function body would grow. */
else if (!e->maybe_hot_p (callee_speedup (e))
+ && growth > param_max_inline_insns_small_and_cold
&& (growth >= inline_insns_single (e->caller, false, false)
|| growth_positive_p (callee, e, growth)))
{
diff --git a/gcc/params.opt b/gcc/params.opt
index 90f9943c8cb..f89b5b2dd5b 100644
--- a/gcc/params.opt
+++ b/gcc/params.opt
@@ -150,6 +150,10 @@ Maximum size (in bytes) of objects tracked bytewise by
dead store elimination.
Common Joined UInteger Var(param_early_inlining_insns) Init(6) Optimization
Param
Maximal estimated growth of function body caused by early inlining of single
call.
+-param=early-inlining-insns-cold=
+Common Joined UInteger Var(param_early_inlining_insns_cold) Init(0)
Optimization Param
+Maximal estimated growth of function body caused by early inlining of cold
call.
+
-param=file-cache-files=
Common Joined UInteger Var(param_file_cache_files) Init(16) Param
Maximum number of files in the file cache.
@@ -654,6 +658,10 @@ The maximum number of instructions when inlining for size.
Common Joined UInteger Var(param_max_inline_insns_small) Optimization Param
The maximum number of instructions when automatically inlining small functions.
+-param=max-inline-insns-small-and-cold=
+Common Joined UInteger Var(param_max_inline_insns_small_and_cold) Optimization
Init(0) Param
+The maximum number of instructions in a small and cold function eligible for
inlining.
+
-param=max-inline-recursive-depth=
Common Joined UInteger Var(param_max_inline_recursive_depth) Optimization
Init(8) Param
The maximum depth of recursive inlining for inline functions.
diff --git a/gcc/testsuite/gcc.dg/inline-cold-1.c
b/gcc/testsuite/gcc.dg/inline-cold-1.c
new file mode 100644
index 00000000000..d7752dc5ec6
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/inline-cold-1.c
@@ -0,0 +1,21 @@
+/* { dg-do compile } */
+/* { dg-options "-Os -fdump-tree-einline-details" }*/
+
+volatile int v;
+
+int
+foo (int x)
+{
+ v += x;
+ v += 1;
+ return v;
+}
+
+int
+main (int argc, char **argv)
+{
+ return foo(argc);
+}
+
+/* { dg-final { scan-tree-dump "will not early inline:
main/\[0-9\]*->foo/\[0-9\]*, call is cold and code would grow by" "einline" } }
*/
+/* { dg-final { scan-tree-dump-not "Inlining foo/\[0-9\]* into main/\[0-9\]*"
"einline" } } */
diff --git a/gcc/testsuite/gcc.dg/inline-cold-2.c
b/gcc/testsuite/gcc.dg/inline-cold-2.c
new file mode 100644
index 00000000000..3de8d18b9c2
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/inline-cold-2.c
@@ -0,0 +1,21 @@
+/* { dg-do compile } */
+/* { dg-options "-Os -fdump-tree-einline-details --param
early-inlining-insns-cold=32" }*/
+
+volatile int v;
+
+int
+foo (int x)
+{
+ v += x;
+ v += 1;
+ return v;
+}
+
+int
+main (int argc, char **argv)
+{
+ return foo(argc);
+}
+
+/* { dg-final { scan-tree-dump "Inlining foo/\[0-9]* into main/\[0-9]*"
"einline" } } */
+/* { dg-final { scan-tree-dump-not "will not early inline: main/\[0-9]* ->
foo/\[0-9]*, call is cold and code would grow by" "einline" } } */
diff --git a/gcc/testsuite/gcc.dg/ipa/inline-cold-1.c
b/gcc/testsuite/gcc.dg/ipa/inline-cold-1.c
new file mode 100644
index 00000000000..27ad518e3bd
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/ipa/inline-cold-1.c
@@ -0,0 +1,21 @@
+/* { dg-do compile } */
+/* { dg-options "-Os -fno-early-inlining -fno-partial-inlining -fno-ipa-cp
-fdump-ipa-inline-details" }*/
+
+volatile int v;
+
+int
+foo (int x)
+{
+ v += x;
+ v += 1;
+ return v;
+}
+
+int
+main (int argc, char **argv)
+{
+ return foo(argc);
+}
+
+/* { dg-final { scan-ipa-dump "not inlinable: main/\[0-9\]* -> foo/\[0-9\]*,
call is unlikely and code size would grow" "inline" } } */
+/* { dg-final { scan-ipa-dump-not "Inlined foo/\[0-9\]* into main/\[0-9\]*"
"inline" } } */
diff --git a/gcc/testsuite/gcc.dg/ipa/inline-cold-2.c
b/gcc/testsuite/gcc.dg/ipa/inline-cold-2.c
new file mode 100644
index 00000000000..6b1ed8bab1b
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/ipa/inline-cold-2.c
@@ -0,0 +1,21 @@
+/* { dg-do compile } */
+/* { dg-options "-Os -fno-early-inlining -fno-partial-inlining -fno-ipa-cp
-fdump-ipa-inline-details --param max-inline-insns-small-and-cold=32" }*/
+
+volatile int v;
+
+int
+foo (int x)
+{
+ v += x;
+ v += 1;
+ return v;
+}
+
+int
+main (int argc, char **argv)
+{
+ return foo(argc);
+}
+
+/* { dg-final { scan-ipa-dump "Inlined foo/\[0-9\]* into main/\[0-9\]*"
"inline" } } */
+/* { dg-final { scan-ipa-dump-not "not inlinable: main/\[0-9\]* ->
foo/\[0-9\]*, call is unlikely and code size would grow" "inline" } } */
--
2.43.0