This is the mail archive of the gcc-patches@gcc.gnu.org mailing list for the GCC project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]

2.95: Dec 21 patch kit



This is where I finally give in and include a few patches to make specific
targets work (or work better) where doing so seems to have a minimal risk.
I'll install this patch kit tomorrow after another set of tests (not all
of these patches have been through a bootstrap yet).

I'm still working on a fix for the sjlj exceptions problem.

	Fri Dec 15 15:32:16 MET 2000  Jan Hubicka  <jh@suse.cz>
	* combine.c (cant_combine_insn_p): Get around SUBREGs when determining
	hardreg<->reg moves.

	2000-12-01  Bernd Schmidt  <bernds@redhat.co.uk>
	* combine.c (cant_combine_insn_p): Only disallow insns involving
	hard regs if they are reg-reg moves.

	2000-11-24  Bernd Schmidt  <bernds@redhat.co.uk>
	* combine.c (cant_combine_insn_p): New function.
	(try_combine): Use it.

Make -mregparm work reliably on x86.  This is used by both glibc and the linux
kernel, so it's only a matter of time until they run into a compiler crash
without this patch.

	1999-12-16  David S. Miller  <davem@redhat.com>
	* expr.c (emit_move_insn_1): Only emit clobbers if one of
	the outputs is a SUBREG.

	Wed Sep 22 17:35:55 1999  Michael Meissner  <meissner@cygnus.com>
	* expr.c (emit_move_insn_1): If we are copying a complex that fits
	in one word or less (complex char, complex short, or on 64 bit
	systems complex float) to/from a hard register, copy it through
	memory instead of dying in gen_{real,imag}part.  If we have a
	short complex type, prevent inlining since it allocates stack
	memory.

From Franz Sirl's patchkit: fixes a number of complex number problems.

	2000-03-06  Mark Mitchell  <mark@codesourcery.com>
	* function.c (free_temps_for_rtl_expr): Don't free slots
	that have been pushed into a higher level.

From Franz Sirl's patchkit, supposed to fix some C++ problems (though
apparently nothing in the testsuite).

	2000-02-08  Geoff Keating  <geoffk@cygnus.com>
	* dwarf2.h (DW_CFA_GNU_negative_offset_extended): New constant.
	* dwarf2out.c (dwarf_cfi_name): Print name of new constant.
	(reg_save): Use DW_CFA_GNU_negative_offset_extended when needed.
	(output_cfi): Handle output of DW_CFA_GNU_negative_offset_extended.
	* frame.c (execute_cfa_insn): Handle
	DW_CFA_GNU_negative_offset_extended.

Suggested by Franz Sirl; according to him it's necessary for EH on ppc-linux
targets.  Can't hurt, since it only gets activated in a place where we'd
trigger an abort without it.

	Fri Sep 10 11:43:07 1999  Philip Blundell <pb@futuretv.com>
	* configure.in, config/arm/linux-oldld.h,
	config/arm/linux-elf26.h, config/arm/linux-elf.h: Backport latest
	ARM GNU/Linux config from mainline.
	* configure: Regenerate.

As suggested by Manfred Hollstein.  I do not have access to an arm-linux
target, so I can't test this.  It can't hurt other arm targets though, so
it seems relatively safe, especially since arm-linux apparently doesn't
work without it anyway.

	* calls.c (emit_call_1): Fall back to call_pop/call_value_pop if no
	non-popping calls are available.

Suggested by Michael Sokolov and various BSD people to fix a spectacular
failure on vax targets.

	* flow.c (propagate_block): Use flow_delete_insn instead of
	NOTEifying a dead ADDR_VEC.

This fixes a regression introduced in one of the previous patchkits (which
in turn fixed a different regression...)  The problem here is that we can't
turn a BARRIER into a NOTE, since a BARRIER doesn't have enough fields.
We'd clobber random memory.


Bernd

Index: combine.c
===================================================================
RCS file: /cvs/gcc/egcs/gcc/combine.c,v
retrieving revision 1.62.4.2
diff -u -p -r1.62.4.2 combine.c
--- combine.c	2000/11/30 11:56:05	1.62.4.2
+++ combine.c	2000/12/21 16:38:17
@@ -392,6 +392,7 @@ static int n_occurrences;
 static void init_reg_last_arrays	PROTO((void));
 static void setup_incoming_promotions   PROTO((void));
 static void set_nonzero_bits_and_sign_copies  PROTO((rtx, rtx));
+static int cant_combine_insn_p	PROTO((rtx));
 static int can_combine_p	PROTO((rtx, rtx, rtx, rtx, rtx *, rtx *));
 static int sets_function_arg_p	PROTO((rtx));
 static int combinable_i3pat	PROTO((rtx, rtx *, rtx, rtx, int, rtx *));
@@ -1312,6 +1313,49 @@ combinable_i3pat (i3, loc, i2dest, i1des
   return 1;
 }

+/* Determine whether INSN can be used in a combination.  Return nonzero if
+   not.  This is used in try_combine to detect early some cases where we
+   can't perform combinations.  */
+
+static int
+cant_combine_insn_p (insn)
+     rtx insn;
+{
+  rtx set;
+  rtx src, dest;
+
+  /* If this isn't really an insn, we can't do anything.
+     This can occur when flow deletes an insn that it has merged into an
+     auto-increment address.  */
+  if (GET_RTX_CLASS (GET_CODE (insn)) != 'i')
+    return 1;
+
+  /* Never combine loads and stores involving hard regs.  The register
+     allocator can usually handle such reg-reg moves by tying.  If we allow
+     the combiner to make substitutions of hard regs, we risk aborting in
+     reload on machines that have SMALL_REGISTER_CLASSES.
+     As an exception, we allow combinations involving fixed regs; these are
+     not available to the register allocator so there's no risk involved.  */
+
+  set = single_set (insn);
+  if (! set)
+    return 0;
+  src = SET_SRC (set);
+  dest = SET_DEST (set);
+  if (GET_CODE (src) == SUBREG)
+    src = SUBREG_REG (src);
+  if (GET_CODE (dest) == SUBREG)
+    dest = SUBREG_REG (dest);
+  if (REG_P (src) && REG_P (dest)
+      && ((REGNO (src) < FIRST_PSEUDO_REGISTER
+	   && ! fixed_regs[REGNO (src)])
+	  || (REGNO (dest) < FIRST_PSEUDO_REGISTER
+	      && ! fixed_regs[REGNO (dest)])))
+    return 1;
+
+  return 0;
+}
+
 /* Try to combine the insns I1 and I2 into I3.
    Here I1 and I2 appear earlier than I3.
    I1 can be zero; then we combine just I2 into I3.
@@ -1362,21 +1406,20 @@ try_combine (i3, i2, i1)
   register rtx link;
   int i;

-  /* If any of I1, I2, and I3 isn't really an insn, we can't do anything.
-     This can occur when flow deletes an insn that it has merged into an
-     auto-increment address.  We also can't do anything if I3 has a
-     REG_LIBCALL note since we don't want to disrupt the contiguity of a
-     libcall.  */
-
-  if (GET_RTX_CLASS (GET_CODE (i3)) != 'i'
-      || GET_RTX_CLASS (GET_CODE (i2)) != 'i'
-      || (i1 && GET_RTX_CLASS (GET_CODE (i1)) != 'i')
+  /* Exit early if one of the insns involved can't be used for
+     combinations.  */
+  if (cant_combine_insn_p (i3)
+      || cant_combine_insn_p (i2)
+      || (i1 && cant_combine_insn_p (i1))
+      /* We also can't do anything if I3 has a
+	 REG_LIBCALL note since we don't want to disrupt the contiguity of a
+	 libcall.  */
 #if 0
       /* ??? This gives worse code, and appears to be unnecessary, since no
 	 pass after flow uses REG_LIBCALL/REG_RETVAL notes.  */
       || find_reg_note (i3, REG_LIBCALL, NULL_RTX)
 #endif
-)
+      )
     return 0;

   combine_attempts++;
Index: dwarf2.h
===================================================================
RCS file: /cvs/gcc/egcs/gcc/dwarf2.h,v
retrieving revision 1.11
diff -u -p -r1.11 dwarf2.h
--- dwarf2.h	1999/01/11 13:43:21	1.11
+++ dwarf2.h	2000/12/21 16:38:17
@@ -1,6 +1,7 @@
 /* Declarations and definitions of codes relating to the DWARF2 symbolic
    debugging information format.
-   Copyright (C) 1992, 1993, 1995, 1996, 1997 Free Software Foundation, Inc.
+   Copyright (C) 1992, 1993, 1995, 1996, 1997, 2000
+   Free Software Foundation, Inc.
    Contributed by Gary Funck (gary@intrepid.com).  Derived from the
    DWARF 1 implementation written by Ron Guilmette (rfg@monkeys.com).

@@ -501,7 +502,8 @@ enum dwarf_call_frame_info

     /* GNU extensions */
     DW_CFA_GNU_window_save = 0x2d,
-    DW_CFA_GNU_args_size = 0x2e
+    DW_CFA_GNU_args_size = 0x2e,
+    DW_CFA_GNU_negative_offset_extended = 0x2f
   };

 #define DW_CIE_ID	  0xffffffff
Index: dwarf2out.c
===================================================================
RCS file: /cvs/gcc/egcs/gcc/dwarf2out.c,v
retrieving revision 1.91.4.5
diff -u -p -r1.91.4.5 dwarf2out.c
--- dwarf2out.c	1999/08/03 07:04:37	1.91.4.5
+++ dwarf2out.c	2000/12/21 16:38:20
@@ -719,6 +719,8 @@ dwarf_cfi_name (cfi_opc)
       return "DW_CFA_GNU_window_save";
     case DW_CFA_GNU_args_size:
       return "DW_CFA_GNU_args_size";
+    case DW_CFA_GNU_negative_offset_extended:
+      return "DW_CFA_GNU_negative_offset_extended";

     default:
       return "DW_CFA_<unknown>";
@@ -948,7 +950,10 @@ reg_save (label, reg, sreg, offset)

       offset /= DWARF_CIE_DATA_ALIGNMENT;
       if (offset < 0)
-	abort ();
+	{
+	  cfi->dw_cfi_opc = DW_CFA_GNU_negative_offset_extended;
+	  offset = -offset;
+	}
       cfi->dw_cfi_oprnd2.dw_cfi_offset = offset;
     }
   else
@@ -1635,6 +1640,7 @@ output_cfi (cfi, fde)
 	  break;
 #endif
 	case DW_CFA_offset_extended:
+	case DW_CFA_GNU_negative_offset_extended:
 	case DW_CFA_def_cfa:
 	  output_uleb128 (cfi->dw_cfi_oprnd1.dw_cfi_reg_num);
           fputc ('\n', asm_out_file);
Index: expr.c
===================================================================
RCS file: /cvs/gcc/egcs/gcc/expr.c,v
retrieving revision 1.144.4.4
diff -u -p -r1.144.4.4 expr.c
--- expr.c	2000/10/27 12:56:40	1.144.4.4
+++ expr.c	2000/12/21 16:38:26
@@ -2679,19 +2679,79 @@ emit_move_insn_1 (x, y)
 	}
       else
 	{
-	  /* Show the output dies here.  This is necessary for pseudos;
+	  rtx realpart_x, realpart_y;
+	  rtx imagpart_x, imagpart_y;
+
+	  /* If this is a complex value with each part being smaller than a
+	     word, the usual calling sequence will likely pack the pieces into
+	     a single register.  Unfortunately, SUBREG of hard registers only
+	     deals in terms of words, so we have a problem converting input
+	     arguments to the CONCAT of two registers that is used elsewhere
+	     for complex values.  If this is before reload, we can copy it into
+	     memory and reload.  FIXME, we should see about using extract and
+	     insert on integer registers, but complex short and complex char
+	     variables should be rarely used.  */
+	  if (GET_MODE_BITSIZE (mode) < 2*BITS_PER_WORD
+	      && (reload_in_progress | reload_completed) == 0)
+	    {
+	      int packed_dest_p = (REG_P (x) && REGNO (x) < FIRST_PSEUDO_REGISTER);
+	      int packed_src_p  = (REG_P (y) && REGNO (y) < FIRST_PSEUDO_REGISTER);
+
+	      if (packed_dest_p || packed_src_p)
+		{
+		  enum mode_class reg_class = ((class == MODE_COMPLEX_FLOAT)
+					       ? MODE_FLOAT : MODE_INT);
+
+		  enum machine_mode reg_mode =
+		    mode_for_size (GET_MODE_BITSIZE (mode), reg_class, 1);
+
+		  if (reg_mode != BLKmode)
+		    {
+		      rtx mem = assign_stack_temp (reg_mode,
+						   GET_MODE_SIZE (mode), 0);
+
+		      rtx cmem = change_address (mem, mode, NULL_RTX);
+
+		      current_function_cannot_inline
+			= "function uses short complex types";
+
+		      if (packed_dest_p)
+			{
+			  rtx sreg = gen_rtx_SUBREG (reg_mode, x, 0);
+			  emit_move_insn_1 (cmem, y);
+			  return emit_move_insn_1 (sreg, mem);
+			}
+		      else
+			{
+			  rtx sreg = gen_rtx_SUBREG (reg_mode, y, 0);
+			  emit_move_insn_1 (mem, sreg);
+			  return emit_move_insn_1 (x, cmem);
+			}
+		    }
+		}
+	    }
+
+	  realpart_x = gen_realpart (submode, x);
+	  realpart_y = gen_realpart (submode, y);
+	  imagpart_x = gen_imagpart (submode, x);
+	  imagpart_y = gen_imagpart (submode, y);
+
+	  /* Show the output dies here.  This is necessary for SUBREGs
+	     of pseudos since we cannot track their lifetimes correctly;
 	     hard regs shouldn't appear here except as return values.
 	     We never want to emit such a clobber after reload.  */
 	  if (x != y
-	      && ! (reload_in_progress || reload_completed))
+	      && ! (reload_in_progress || reload_completed)
+	      && (GET_CODE (realpart_x) == SUBREG
+		  || GET_CODE (imagpart_x) == SUBREG))
 	    {
 	      emit_insn (gen_rtx_CLOBBER (VOIDmode, x));
 	    }

 	  emit_insn (GEN_FCN (mov_optab->handlers[(int) submode].insn_code)
-		     (gen_realpart (submode, x), gen_realpart (submode, y)));
+		     (realpart_x, realpart_y));
 	  emit_insn (GEN_FCN (mov_optab->handlers[(int) submode].insn_code)
-		     (gen_imagpart (submode, x), gen_imagpart (submode, y)));
+		     (imagpart_x, imagpart_y));
 	}

       return get_last_insn ();
@@ -2703,6 +2763,8 @@ emit_move_insn_1 (x, y)
   else if (GET_MODE_SIZE (mode) > UNITS_PER_WORD)
     {
       rtx last_insn = 0;
+      rtx seq;
+      int need_clobber;

 #ifdef PUSH_ROUNDING

@@ -2715,15 +2777,9 @@ emit_move_insn_1 (x, y)
 	}
 #endif

-      /* Show the output dies here.  This is necessary for pseudos;
-	 hard regs shouldn't appear here except as return values.
-	 We never want to emit such a clobber after reload.  */
-      if (x != y
-	  && ! (reload_in_progress || reload_completed))
-	{
-	  emit_insn (gen_rtx_CLOBBER (VOIDmode, x));
-	}
+      start_sequence ();

+      need_clobber = 0;
       for (i = 0;
 	   i < (GET_MODE_SIZE (mode)  + (UNITS_PER_WORD - 1)) / UNITS_PER_WORD;
 	   i++)
@@ -2745,8 +2801,26 @@ emit_move_insn_1 (x, y)
 	  if (xpart == 0 || ypart == 0)
 	    abort ();

+	  need_clobber |= (GET_CODE (xpart) == SUBREG);
+
 	  last_insn = emit_move_insn (xpart, ypart);
 	}
+
+      seq = gen_sequence ();
+      end_sequence ();
+
+      /* Show the output dies here.  This is necessary for SUBREGs
+	 of pseudos since we cannot track their lifetimes correctly;
+	 hard regs shouldn't appear here except as return values.
+	 We never want to emit such a clobber after reload.  */
+      if (x != y
+	  && ! (reload_in_progress || reload_completed)
+	  && need_clobber != 0)
+	{
+	  emit_insn (gen_rtx_CLOBBER (VOIDmode, x));
+	}
+
+      emit_insn (seq);

       return last_insn;
     }
Index: flow.c
===================================================================
RCS file: /cvs/gcc/egcs/gcc/flow.c,v
retrieving revision 1.120.4.5
diff -u -p -r1.120.4.5 flow.c
--- flow.c	2000/12/18 14:34:03	1.120.4.5
+++ flow.c	2000/12/21 16:38:28
@@ -2763,17 +2763,8 @@ propagate_block (old, first, last, final
 			  int i;
 			  for (i = 0; i < len; i++)
 			    LABEL_NUSES (XEXP (XVECEXP (pat, diff_vec_p, i), 0))--;
-			  PUT_CODE (next, NOTE);
-			  NOTE_LINE_NUMBER (next) = NOTE_INSN_DELETED;
-			  NOTE_SOURCE_FILE (next) = 0;

-			  if ((next = next_nonnote_insn (label)) != NULL
-			      && GET_CODE (next) == BARRIER)
-			    {
-			      PUT_CODE (next, NOTE);
-			      NOTE_LINE_NUMBER (next) = NOTE_INSN_DELETED;
-			      NOTE_SOURCE_FILE (next) = 0;
-			    }
+			  flow_delete_insn (next);
 			}
 		    }
 		}
Index: frame.c
===================================================================
RCS file: /cvs/gcc/egcs/gcc/frame.c,v
retrieving revision 1.25
diff -u -p -r1.25 frame.c
--- frame.c	1998/12/16 20:55:48	1.25
+++ frame.c	2000/12/21 16:38:28
@@ -714,6 +714,14 @@ execute_cfa_insn (void *p, struct frame_
       state->s.args_size = offset;
       break;

+    case DW_CFA_GNU_negative_offset_extended:
+      p = decode_uleb128 (p, &reg);
+      p = decode_uleb128 (p, &offset);
+      offset *= info->data_align;
+      state->s.saved[reg] = REG_SAVED_OFFSET;
+      state->s.reg_or_offset[reg] = -offset;
+      break;
+
     default:
       abort ();
     }
Index: function.c
===================================================================
RCS file: /cvs/gcc/egcs/gcc/function.c,v
retrieving revision 1.90.4.3
diff -u -p -r1.90.4.3 function.c
--- function.c	2000/05/24 06:01:57	1.90.4.3
+++ function.c	2000/12/21 16:38:30
@@ -1428,7 +1428,16 @@ free_temps_for_rtl_expr (t)

   for (p = temp_slots; p; p = p->next)
     if (p->rtl_expr == t)
-      p->in_use = 0;
+      {
+	/* If this slot is below the current TEMP_SLOT_LEVEL, then it
+	   needs to be preserved.  This can happen if a temporary in
+	   the RTL_EXPR was addressed; preserve_temp_slots will move
+	   the temporary into a higher level.   */
+	if (temp_slot_level <= p->level)
+	  p->in_use = 0;
+	else
+	  p->rtl_expr = NULL_TREE;
+      }

   combine_temp_slots ();
 }
diff -rupN -x CVS -x RCS -x *.o -x *.info* -x *.html* -x *.elc -x *.dvi -x *.orig -x *~ -x version.el gcc-2.95.3.orig/gcc/config/arm/linux-elf.h gcc-2.95.3/gcc/config/arm/linux-elf.h
--- gcc-2.95.3.orig/gcc/config/arm/linux-elf.h	Wed Dec 20 13:59:36 2000
+++ gcc-2.95.3/gcc/config/arm/linux-elf.h	Thu Dec 21 17:37:16 2000
@@ -28,13 +28,30 @@ Boston, MA 02111-1307, USA.  */
 /* We have libgcc2.  */
 #define HAVE_ATEXIT

-/* Default is to use APCS-32 mode.  */
 #ifndef SUBTARGET_DEFAULT_APCS26
-#define TARGET_DEFAULT (ARM_FLAG_APCS_32 | ARM_FLAG_SHORT_BYTE)
-#define SUBTARGET_EXTRA_LINK_SPEC	\
+/* Default is to use APCS-32 mode.  */
+# define TARGET_DEFAULT (ARM_FLAG_APCS_32 | ARM_FLAG_SHORT_BYTE)
+# ifdef SUBTARGET_OLD_LINKER
+#  define SUBTARGET_EXTRA_LINK_SPEC	\
 	" %{mapcs-26:-m elf32arm26} %{!mapcs-26:-m elf32arm}"
-#define SUBTARGET_EXTRA_ASM_SPEC	\
+# else	/* new linker */
+#  define SUBTARGET_EXTRA_LINK_SPEC	\
+	" %{mapcs-26:-m armelf_linux26} %{!mapcs-26:-m armelf_linux} -p"
+# endif
+# define SUBTARGET_EXTRA_ASM_SPEC	\
 	" %{mapcs-26:-mapcs-26} %(!mapcs-26:-mapcs-32}"
+# define CPP_APCS_PC_DEFAULT_SPEC "-D__APCS_32__"
+#else	/* default is APCS-26 */
+# define TARGET_DEFAULT (ARM_FLAG_SHORT_BYTE)
+# ifdef SUBTARGET_OLD_LINKER
+#  define SUBTARGET_LINK_SPEC	\
+	" %{mapcs-32:-m elf32arm} %{!mapcs-32:-m elf32arm26}"
+# else	/* new linker */
+#  define SUBTARGET_LINK_SPEC	\
+	" %{mapcs-32:-m armelf_linux} %{!mapcs-32:-m armelf_linux26} -p"
+# endif
+# define SUBTARGET_EXTRA_ASM_SPEC	\
+	" %{mapcs-32:-mapcs-32} %(!mapcs-32:-mapcs-26}"
 #endif

 /* This was defined in linux.h.  Define it here also. */
diff -rupN -x CVS -x RCS -x *.o -x *.info* -x *.html* -x *.elc -x *.dvi -x *.orig -x *~ -x version.el gcc-2.95.3.orig/gcc/config/arm/linux-elf26.h gcc-2.95.3/gcc/config/arm/linux-elf26.h
--- gcc-2.95.3.orig/gcc/config/arm/linux-elf26.h	Sat Dec 19 10:11:45 1998
+++ gcc-2.95.3/gcc/config/arm/linux-elf26.h	Thu Dec 21 12:43:01 2000
@@ -1,6 +1,7 @@
-/* Definitions for 26-bit ARM running Linux-based GNU systems using ELF
-   Copyright (C) 1998 Free Software Foundation, Inc.
-   Contributed by Philip Blundell <philb@gnu.org>
+/* Definitions for ARM running Linux-based GNU systems
+   using ELF and 26-bit APCS.
+   Copyright (C) 1999 Free Software Foundation, Inc.
+   Contributed by Philip Blundell <Philip.Blundell@pobox.com>

 This file is part of GNU CC.

@@ -19,14 +20,5 @@ along with this program; see the file CO
 the Free Software Foundation, 59 Temple Place - Suite 330,
 Boston, MA 02111-1307, USA.  */

+/* Tell linux-elf.h to default to 26-bit mode.  */
 #define SUBTARGET_DEFAULT_APCS26
-
-#define SUBTARGET_LINK_SPEC	\
-	" %{mapcs-32:-m elf32arm} %{!mapcs-32:-m elf32arm26}"
-
-#define SUBTARGET_EXTRA_ASM_SPEC	\
-	" %{mapcs-32:-mapcs-32} %(!mapcs-32:-mapcs-26}"
-
-#define TARGET_DEFAULT (ARM_FLAG_SHORT_BYTE)
-
-#include "arm/linux-elf.h"
diff -rupN -x CVS -x RCS -x *.o -x *.info* -x *.html* -x *.elc -x *.dvi -x *.orig -x *~ -x version.el gcc-2.95.3.orig/gcc/config/arm/linux-elf26.h gcc-2.95.3/gcc/config/arm/linux-elf26.h
--- gcc-2.95.3.orig/gcc/config/arm/linux-oldld.h	Tue Nov  7 16:06:25 2000
+++ gcc-2.95.3/gcc/config/arm/linux-oldld.h
@@ -0,0 +1,27 @@
+/* Definitions for ARM running Linux-based GNU systems
+   using ELF with old binutils.
+   Copyright (C) 1999 Free Software Foundation, Inc.
+   Contributed by Philip Blundell <Philip.Blundell@pobox.com>
+
+This file is part of GNU CC.
+
+GNU CC is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GNU CC is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with this program; see the file COPYING.  If not, write to
+the Free Software Foundation, 59 Temple Place - Suite 330,
+Boston, MA 02111-1307, USA.  */
+
+/* Unfortunately, owing to various historical accidents, version 2.9.4
+   and newer of GNU binutils are not quite compatible with the old
+   (2.9.1-based) toolset.  This tells linux-elf.h to generate specs
+   appropriate for the older versions.  */
+#define SUBTARGET_OLD_LINKER
diff -rupN -x CVS -x RCS -x *.o -x *.info* -x *.html* -x *.elc -x *.dvi -x *.orig -x *~ -x version.el gcc-2.95.3.orig/gcc/configure.in gcc-2.95.3/gcc/configure.in
--- gcc-2.95.3.orig/gcc/configure.in	Tue Jan 11 09:21:04 2000
+++ gcc-2.95.3/gcc/configure.in	Thu Dec 21 12:43:01 2000
@@ -756,15 +756,31 @@ changequote([,])dnl
 		tmake_file=arm/t-linux
 		gnu_ld=yes
 		;;
-	arm*-*-linux-gnu*)		# ARM GNU/Linux with ELF
+	arm*-*-linux-gnuoldld*)		# ARM GNU/Linux with old ELF linker
 		xm_file=arm/xm-linux.h
 		xmake_file=x-linux
+		tm_file="arm/linux-oldld.h arm/linux-elf.h"
 		case $machine in
 		armv2*-*-*)
-			tm_file=arm/linux-elf26.h
+			tm_file="arm/linux-elf26.h $tm_file"
+			;;
+		esac
+		tmake_file="t-linux arm/t-linux"
+		extra_parts="crtbegin.o crtbeginS.o crtend.o crtendS.o"
+		gnu_ld=yes
+		case x${enable_threads} in
+		x | xyes | xpthreads | xposix)
+			thread_file='posix'
 			;;
-		*)
-			tm_file=arm/linux-elf.h
+		esac
+		;;
+	arm*-*-linux-gnu*)		# ARM GNU/Linux with ELF
+		xm_file=arm/xm-linux.h
+		xmake_file=x-linux
+		tm_file="arm/linux-elf.h"
+		case $machine in
+		armv2*-*-*)
+			tm_file="arm/linux-elf26.h $tm_file"
 			;;
 		esac
 		tmake_file="t-linux arm/t-linux"
diff -rupN -x CVS -x RCS -x *.o -x *.info* -x *.html* -x *.elc -x *.dvi -x *.orig -x *~ -x version.el gcc-2.95.3.orig/gcc/configure gcc-2.95.3/gcc/configure
--- gcc-2.95.3.orig/gcc/configure	Sat Jul  8 16:04:38 2000
+++ gcc-2.95.3/gcc/configure	Thu Dec 21 12:43:01 2000
@@ -3194,15 +3194,31 @@ for machine in $build $host $target; do
 		tmake_file=arm/t-linux
 		gnu_ld=yes
 		;;
-	arm*-*-linux-gnu*)		# ARM GNU/Linux with ELF
+	arm*-*-linux-gnuoldld*)		# ARM GNU/Linux with old ELF linker
 		xm_file=arm/xm-linux.h
 		xmake_file=x-linux
+		tm_file="arm/linux-oldld.h arm/linux-elf.h"
 		case $machine in
 		armv2*-*-*)
-			tm_file=arm/linux-elf26.h
+			tm_file="arm/linux-elf26.h $tm_file"
+			;;
+		esac
+		tmake_file="t-linux arm/t-linux"
+		extra_parts="crtbegin.o crtbeginS.o crtend.o crtendS.o"
+		gnu_ld=yes
+		case x${enable_threads} in
+		x | xyes | xpthreads | xposix)
+			thread_file='posix'
 			;;
-		*)
-			tm_file=arm/linux-elf.h
+		esac
+		;;
+	arm*-*-linux-gnu*)		# ARM GNU/Linux with ELF
+		xm_file=arm/xm-linux.h
+		xmake_file=x-linux
+		tm_file="arm/linux-elf.h"
+		case $machine in
+		armv2*-*-*)
+			tm_file="arm/linux-elf26.h $tm_file"
 			;;
 		esac
 		tmake_file="t-linux arm/t-linux"

Index: calls.c
===================================================================
RCS file: /cvs/gcc/egcs/gcc/calls.c,v
retrieving revision 1.57
diff -u -p -r1.57 calls.c
--- calls.c	1999/05/08 01:58:39	1.57
+++ calls.c	2000/12/21 17:21:17
@@ -405,7 +405,15 @@ emit_call_1 (funexp, fndecl, funtype, st

 #ifndef ACCUMULATE_OUTGOING_ARGS
 #if defined (HAVE_call_pop) && defined (HAVE_call_value_pop)
-  if (HAVE_call_pop && HAVE_call_value_pop && n_popped > 0)
+/* If the target has "call" or "call_value" insns, then prefer them
+   if no arguments are actually popped.  If the target does not have
+   "call" or "call_value" insns, then we must use the popping versions
+   even if the call has no arguments to pop.  */
+  if (HAVE_call_pop && HAVE_call_value_pop
+#if defined (HAVE_call) && defined (HAVE_call_value)
+      && (n_popped > 0 || ! HAVE_call || ! HAVE_call_value)
+#endif
+      )
     {
       rtx n_pop = GEN_INT (n_popped);
       rtx pat;


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]