i386.h (MACHINE_DEPENDENT_REORG): New macro.
authorJan Hubicka <jh@suse.cz>
Tue, 16 Jul 2002 22:20:10 +0000 (00:20 +0200)
committerJan Hubicka <hubicka@gcc.gnu.org>
Tue, 16 Jul 2002 22:20:10 +0000 (22:20 +0000)
* i386.h (MACHINE_DEPENDENT_REORG): New macro.
* i386.c (x86_machine_dependent_reorg): New function.
* i386-protos.h (x86_machine_dependent_reorg): Declare.

From-SVN: r55498

gcc/ChangeLog
gcc/config/i386/i386-protos.h
gcc/config/i386/i386.c
gcc/config/i386/i386.h

index 5c0fddd16a69138eed63619bd8311ea532b69021..3939b6117c8b0d8bed94fa1891da9eb920ed42c1 100644 (file)
@@ -1,3 +1,9 @@
+Wed Jul 17 00:19:20 CEST 2002  Jan Hubicka  <jh@suse.cz>
+
+       * i386.h (MACHINE_DEPENDENT_REORG): New macro.
+       * i386.c (x86_machine_dependent_reorg): New function.
+       * i386-protos.h (x86_machine_dependent_reorg): Declare.
+
 2002-07-16  Zack Weinberg  <zack@codesourcery.com>
 
        * builtins.c (std_expand_builtin_va_start): Remove unused
index d49ce1a71f3b742e9db1e8996936323cece4bb3f..a81e0f537b2c009f3ff68153ac8294ee01c625a9 100644 (file)
@@ -209,6 +209,7 @@ extern int x86_field_alignment PARAMS ((tree, int));
 #endif
 
 extern rtx ix86_tls_get_addr PARAMS ((void));
+extern void x86_machine_dependent_reorg PARAMS ((rtx));
 
 /* In winnt.c  */
 extern void i386_pe_encode_section_info PARAMS ((tree, int));
index 5c49f175dc91ef46941f11179d9582bba2eaa153..6e19b5cd887ef0c1638210dcb2161a0e3cb9550b 100644 (file)
@@ -13677,4 +13677,47 @@ x86_field_alignment (field, computed)
   return computed;
 }
 
+/* Implement machine specific optimizations.  
+   At the moment we implement single transformation: AMD Athlon works faster
+   when RET is not destination of conditional jump or directly preceeded
+   by other jump instruction.  We avoid the penalty by inserting NOP just
+   before the RET instructions in such cases.  */
+void
+x86_machine_dependent_reorg (first)
+     rtx first ATTRIBUTE_UNUSED;
+{
+  edge e;
+
+  if (!TARGET_ATHLON || !optimize || optimize_size)
+    return;
+  for (e = EXIT_BLOCK_PTR->pred; e; e = e->pred_next)
+  {
+    basic_block bb = e->src;
+    rtx ret = bb->end;
+    rtx prev;
+    bool insert = false;
+
+    if (!returnjump_p (ret) || !maybe_hot_bb_p (bb))
+      continue;
+    prev = prev_nonnote_insn (ret);
+    if (prev && GET_CODE (prev) == CODE_LABEL)
+      {
+       edge e;
+       for (e = bb->pred; e; e = e->pred_next)
+         if (EDGE_FREQUENCY (e) && e->src->index > 0
+             && !(e->flags & EDGE_FALLTHRU))
+           insert = 1;
+      }
+    if (!insert)
+      {
+       prev = prev_real_insn (ret);
+       if (prev && GET_CODE (prev) == JUMP_INSN
+           && any_condjump_p (prev))
+         insert = 1;
+      }
+    if (insert)
+      emit_insn_before (gen_nop (), ret);
+  }
+}
+
 #include "gt-i386.h"
index be4e1b6cab5eb1ad68cd39e4fc47e0b54e1e0909..7cf972194fed40bfac1400b47fdf8c7bc466a3f7 100644 (file)
@@ -3354,6 +3354,7 @@ enum fp_cw_mode {FP_CW_STORED, FP_CW_UNINITIALIZED, FP_CW_ANY};
    ((SRC) < FIRST_STACK_REG || (SRC) > LAST_STACK_REG)
 
 \f
+#define MACHINE_DEPENDENT_REORG(X) x86_machine_dependent_reorg(X)
 /*
 Local variables:
 version-control: t