summaryrefslogtreecommitdiffstats
path: root/contrib/gcc
diff options
context:
space:
mode:
authorkan <kan@FreeBSD.org>2002-10-10 04:40:18 +0000
committerkan <kan@FreeBSD.org>2002-10-10 04:40:18 +0000
commit369fa8676085c5c326cdf3cad77db1f51c7e6477 (patch)
tree0308ef86572f5270d39d906e7542cf277b57db76 /contrib/gcc
parentcd461831013b09cb2e709690544dc50ced9ddd0a (diff)
parent92318bc515d223b2eeebb665f76e131dd2318b2b (diff)
downloadFreeBSD-src-369fa8676085c5c326cdf3cad77db1f51c7e6477.zip
FreeBSD-src-369fa8676085c5c326cdf3cad77db1f51c7e6477.tar.gz
This commit was generated by cvs2svn to compensate for changes in r104752,
which included commits to RCS files with non-trunk default branches.
Diffstat (limited to 'contrib/gcc')
-rw-r--r--contrib/gcc/ChangeLog336
-rw-r--r--contrib/gcc/c-objc-common.c8
-rw-r--r--contrib/gcc/calls.c8
-rw-r--r--contrib/gcc/config/arm/arm.h14
-rw-r--r--contrib/gcc/config/arm/arm.md9
-rw-r--r--contrib/gcc/config/i386/linux64.h19
-rw-r--r--contrib/gcc/config/i386/t-linux643
-rw-r--r--contrib/gcc/config/i386/winnt.c19
-rw-r--r--contrib/gcc/config/rs6000/rs6000.md2
-rw-r--r--contrib/gcc/config/sparc/linux64.h67
-rw-r--r--contrib/gcc/config/sparc/sol2-bi.h29
-rw-r--r--contrib/gcc/config/sparc/sparc.c1
-rw-r--r--contrib/gcc/config/sparc/sparc.md25
-rw-r--r--contrib/gcc/config/sparc/t-linux6414
-rw-r--r--contrib/gcc/config/sparc/t-sol2-643
-rw-r--r--contrib/gcc/cp/ChangeLog85
-rw-r--r--contrib/gcc/cp/cp-tree.h26
-rw-r--r--contrib/gcc/cp/decl2.c39
-rw-r--r--contrib/gcc/cp/init.c5
-rw-r--r--contrib/gcc/cp/pt.c42
-rw-r--r--contrib/gcc/cpplib.c57
-rw-r--r--contrib/gcc/cppmacro.c6
-rw-r--r--contrib/gcc/doc/cpp.texi37
-rw-r--r--contrib/gcc/doc/extend.texi74
-rw-r--r--contrib/gcc/doc/invoke.texi22
-rw-r--r--contrib/gcc/doloop.c93
-rw-r--r--contrib/gcc/expr.c126
-rw-r--r--contrib/gcc/f/version.c2
-rw-r--r--contrib/gcc/genmultilib70
-rw-r--r--contrib/gcc/jump.c12
-rw-r--r--contrib/gcc/loop.c540
-rw-r--r--contrib/gcc/loop.h3
-rw-r--r--contrib/gcc/mklibgcc.in70
-rw-r--r--contrib/gcc/reload1.c22
-rw-r--r--contrib/gcc/rtl.h1
-rw-r--r--contrib/gcc/sched-deps.c10
-rw-r--r--contrib/gcc/sibcall.c13
-rw-r--r--contrib/gcc/tree.h27
-rw-r--r--contrib/gcc/unroll.c13
-rw-r--r--contrib/gcc/varasm.c2
40 files changed, 1233 insertions, 721 deletions
diff --git a/contrib/gcc/ChangeLog b/contrib/gcc/ChangeLog
index 783f3d1..44f9438 100644
--- a/contrib/gcc/ChangeLog
+++ b/contrib/gcc/ChangeLog
@@ -1,3 +1,335 @@
+2002-10-09 Zack Weinberg <zack@codesourcery.com>
+
+ PR c/7353
+ * c-decl.c (start_decl): Unconditionally issue error for
+ 'typedef foo = bar'.
+ (finish_decl): Remove special case for TYPE_DECL with initializer.
+
+ * doc/extend.texi: Delete "Naming Types" section. Change all
+ cross-references to that section to refer to "Typeof" instead.
+ Add the useful safe-max()-macro example from "Naming Types" to
+ "Typeof", rewritten using that extension. Add some compatibility
+ notes to "Typeof."
+
+2002-10-02 Richard Henderson <rth@redhat.com>
+
+ PR opt/7124
+ * config/i386/i386.c (ix86_register_move_cost): Increase cost
+ for secondary_memory_needed pairs.
+
+Wed Oct 9 19:09:13 CEST 2002 Jan Hubicka <jh@suse.cz>
+
+ PR opt/7912
+ PR opt/7390
+ * i386.c (athlon_cost): Fix the move costs.
+
+2002-10-09 Alan Modra <amodra@bigpond.net.au>
+
+ * libgcc2.c (__floatdisf): Properly cure double rounding.
+
+2002-10-09 Gabriel Dos Reis <gdr@integrable-solutions.net>
+
+ PR doc/7484
+ * doc/invoke.texi (Option Summary): List
+ -Wmissing-declarations as a C only option.
+
+2002-10-08 Jakub Jelinek <jakub@redhat.com>
+
+ * config/sparc/t-linux64 (MULTILIB_OPTIONS): Remove
+ mno-app-regs|mcmodel=medany.
+ (MULTILIB_DIRNAMES, MULTILIB_OSDIRNAMES): Remove alt.
+ (MULTILIB_EXCEPTIONS, MULTILIB_EXCLUSIONS, MULTILIB_MATCHES): Remove.
+ (CRTSTUFF_T_CFLAGS): Define.
+
+2002-09-25 Eric Botcazou <ebotcazou@libertysurf.fr>
+ Volker Reichelt <reichelt@igpm.rwth-aachen.de>
+
+ PR c/7411
+ * expr.c (expand_expr) [PLUS]: Simplify after the operands
+ have been expanded in EXPAND_NORMAL mode.
+
+2002-10-06 Richard Henderson <rth@redhat.com>
+
+ * config/rs6000/rs6000.md (load_toc_v4_PIC_2): Fix base constraint.
+
+2002-10-06 Roger Sayle <roger@eyesopen.com>
+
+ PR optimization/6627
+ * toplev.c (force_align_functions_log): New global variable.
+ * flags.h (force_align_functions_log): Add extern prototype.
+ * varasm.c (assemble_start_function): Use it to force minimum
+ function alignment.
+ * config/i386/i386.h (FUNCTION_BOUNDARY): Set the correct
+ minimum function alignment to one byte.
+ (TARGET_PTRMEMFUNC_VBIT_LOCATION): Store the virtual bit in
+ the least significant bit of vtable member function pointers.
+ * tree.h (enum ptrmemfunc_vbit_where_t): Move definition to
+ here from cp/cp-tree.h.
+
+2002-10-06 Neil Booth <neil@daikokuya.co.uk>
+
+ Debian BTS Bug #157416
+ * cpplib.c (destringize_and_run): Kludge around getting
+ tokens from in-progress macros.
+ (_cpp_do__Pragma): Simplify.
+
+2002-10-06 Frank Ch. Eigler <fche@redhat.com>
+
+ * cppinit.c (init_standard_includes, parse_option): Use strncmp.
+
+2002-10-05 Jakub Jelinek <jakub@redhat.com>
+
+ * gcc.c (set_multilib_dir): Don't access *end.
+ Use memcpy instead of strncpy. Don't write beyond malloced buffer.
+ (print_multilib_info): Don't show paths starting with ".:".
+ * genmultilib: Add new option, "yes" if multilibs are enabled.
+ Update comments. If multilibs not enabled, print .:${osdirout}
+ for each directory. If multilibs are enabled, always print
+ ${dirout}:${osdirout}, even if the two are the same.
+ * Makefile.in (s-mlib): Pass @enable_multilib@ to genmultilib.
+ Pass all MULTILIB_* variables to genmultilib even if
+ --disable-multilib but MULTILIB_OSDIRNAMES is not empty.
+
+ * gcc.c (print_multi_os_directory): New variable.
+ (option_map): Support --print-multi-os-directory.
+ (struct prefix_list): Add os_multilib field.
+ (multilib_os_dir): New variable.
+ (static_specs): Add multilib_options.
+ (find_a_file): Add multilib argument. Search in GCC or OS multilib
+ subdirs if non-zero.
+ (read_specs, execute): Update callers.
+ (find_file): Likewise. Don't prefix name with multilib_dir, instead
+ pass 1 as multilib option.
+ (display_help): Include --print-multi-os-directory.
+ (add_prefix): Add os_multilib argument. Initialize pl->os_multilib.
+ (process_command): Update callers. Handle --print-multi-os-directory.
+ (do_spec_1) ['D']: Use multilib_os_directory if pl->os_multilib is
+ set.
+ (main): Update find_a_file and add_prefix callers.
+ Handle print_multi_os_directory.
+ (struct mdswitchstr): New.
+ (mdswitches, n_mdswitches): New variables.
+ (used_arg): Add MULTILIB_DEFAULT switches too if they are not
+ present on the command line nor their mutually incompatible
+ switches.
+ (default_arg): Optimize.
+ (set_multilib_dir): Compute multilib_os_dir. Initialize mdswitches
+ array.
+ (print_multilib_info): Only print GCC multilib dir name, not OS
+ multilib dirname.
+ * genmultilib: Add osdirnames parameter. Output multilib_options
+ variable. If osdirnames is specified, output dirnames as
+ dirname:osdirname.
+ * mklibgcc.in: Use MULTILIB_OSDIRNAMES, --print-multi-directory
+ and --print-multi-os-directory instead of SHLIB_SLIBDIR_SUFFIXES
+ to compute libgcc_s soname and install path.
+ * Makefile.in (libgcc.mk): Pass MULTILIB_OSDIRNAMES instead of
+ SHLIB_SLIBDIR_SUFFIXES to mklibgcc.
+ (s_mlib): Pass MULTILIB_OSDIRNAMES or nothing as last genmultilib
+ argument.
+
+ * config/sparc/t-linux64 (MULTILIB_OSDIRNAMES): Set.
+ (SHLIB_SLIBDIR_SUFFIXES): Remove.
+ * config/sparc/linux64.h (STARTFILE_SPEC32, STARTFILE_SPEC64,
+ ENDFILE_SPEC32, ENDFILE_SPEC64, ENDFILE_COMMON): Remove.
+ (STARTFILE_SPEC, ENDFILE_SPEC): Don't distinguish between -m32
+ and -m64.
+ * config/sparc/t-sol2-64 (MULTILIB_OSDIRNAMES): Set.
+ (SHLIB_SLIBDIR_SUFFIXES): Remove.
+ * config/sparc/sol2-bi.h (STARTFILE_SPEC32, STARTFILE_SPEC64): Remove.
+ (STARTFILE_ARCH_SPEC): Remove.
+ (STARTFILE_SPEC): Add values-X*.o here.
+ * config/i386/t-linux64 (MULTILIB_OSDIRNAMES): Set.
+ (SHLIB_SLIBDIR_SUFFIXES): Remove.
+ * config/i386/linux64.h (STARTFILE_PREFIX_SPEC): Remove.
+ (STARTFILE_SPEC, ENDFILE_SPEC): Don't distinguish between m32 and
+ !m32.
+ * config/mips/t-iris6 (MULTILIB_OSDIRNAMES): Set.
+ (SHLIB_SLIBDIR_SUFFIXES): Remove.
+
+2002-10-05 Neil Booth <neil@daikokuya.co.uk>
+
+ PR preprocessor/8120
+ * doc/cpp.texi: Update documentation of bad use of ##.
+
+Thu Oct 3 23:15:15 CEST 2002 Jan Hubicka <jh@suse.cz>
+
+ * i386.h (CPP_SPECS): fix defines for -msse, -msse2, -mpentium2,3.
+
+Thu Oct 3 21:35:36 CEST 2002 Jan Hubicka <jh@suse.cz>
+
+ * toplev.c (rest_of_compilation): Dump loops before clobbering
+ the structure.
+
+ * expr.c (force_operand): Use expand_simple_* to handle more
+ cases.
+
+ * i386.c (q_regs_operand): Use ANY_QI_REG_P.
+
+ * i386.c (override_options): Fix stack alignment.
+ (classify_argument): Handle variable sized types.
+ (ix86_expand_int_movcc): Avoid RTL sharing problem.
+
+ * i386.md (prefetch_sse_rex, prefetch_3dnow_rex): New.
+ (prefetch): Properly handle 64bit case.
+
+ * i386.c (classify_argument): Properly compute word size of the analyzed object.
+
+ * jump.c (reg_or_subregno): New function.
+ * rtl.h (reg_or_subregno): Declare
+ * unroll.c (find_splittable_givs): Handle subregs.
+
+ Richard Sandiford <rsandifo@redhat.com>:
+
+ * expr.c (force_operand): Fix reversed move.
+
+ Andreas Jaeger <aj@suse.de>:
+
+ * config/i386/linux64.h (STARTFILE_PREFIX_SPEC): New.
+
+ Janis Johnson <janis187@us.ibm.com>:
+
+ * loop.c (emit_prefetch_instructions): Several small fixes.
+
+Thu Sep 5 00:34:33 2002 J"orn Rennecke <joern.rennecke@superh.com>
+
+ * loop.c (scan_loop): Don't mark separate insns out of a libcall
+ for moving.
+ (move_movables): Abort if we see the first insn of a libcall.
+
+2002-10-01 David S. Miller <davem@redhat.com>
+
+ PR middle-end/7151
+ * config/sparc/sparc.md (movdi_insn_sp32_v9): Accept 'e' regs.
+ (movdi reg/reg split): Match only on sparc32, and v9 when int regs.
+
+2002-10-01 David S. Miller <davem@redhat.com>
+ Jan Hubicka <jh@suse.cz>
+
+ * reload1.c (gen_reload:SECONDARY_MEMORY_NEEDED): Handle SUBREG.
+ * reload.c (push_reload:SECONDARY_MEMORY_NEEDED): Likewise.
+
+2002-09-30 Bob Wilson <bob.wilson@acm.org>
+
+ * config/xtensa/xtensa.h (REG_CLASS_NAMES, REG_CLASS_CONTENTS):
+ Add new RL_REGS register class.
+ (PREFERRED_RELOAD_CLASS, PREFERRED_OUTPUT_RELOAD_CLASS):
+ Call xtensa_preferred_reload_class for both input and output reloads.
+ * config/xtensa/xtensa.c (xtensa_regno_to_class): Use new RL_REGS class.
+ (xtensa_preferred_reload_class): Handle output reloads; use RL_REGS
+ instead of either AR_REGS or GR_REGS classes.
+ (xtensa_secondary_reload_class): Use new RL_REGS class.
+ * config/xtensa/xtensa-protos.h (xtensa_preferred_reload_class): Update.
+
+2002-08-21 John David Anglin <dave@hiauly1.hia.nrc.ca>
+
+ * cppinit.c (remove_dup_nonsys_dirs): Fix warning and return value.
+
+2002-08-20 John David Anglin <dave@hiauly1.hia.nrc.ca>
+
+ * cppinit.c (remove_dup_dir): Add head_ptr argument to handle removal
+ at head.
+ (remove_dup_nonsys_dirs): New function.
+ (remove_dup_dirs): Change argument head to head_ptr. Remove warnings.
+ (merge_include_chains): Remove non-system include directories from
+ quote and bracket include chains when they duplicate equivalent system
+ directories.
+ * doc/cpp.texi (-I): Update.
+ * doc/cppopts.texi (-I): Update.
+ * doc/install.texi (--with-local-prefix): Further document usage of
+ this option.
+ * doc/invoke.texi (-I): Update.
+
+2002-09-30 Richard Earnshaw <rearnsha@arm.com>
+
+ * arm.h (BASE_REG_CLASS): Always return LO_REGS for Thumb.
+ (MODE_BASE_REG_CLASS, case Thumb): Only return BASE_REGS if we know
+ that we have a SImode access, and only then if reload hasn't completed;
+ for all other cases, use LO_REGS.
+
+2002-09-29 David S. Miller <davem@redhat.com>
+
+ * config/sparc/linux64.h (STARTFILE_SPEC32, ENDFILE_SPEC32): Kill
+ hardcoded paths.
+
+2002-09-27 Alexander N. Kabaev <ak03@gte.com>
+
+ PR preprocessor/8055
+ * cppmacro.c (stringify_arg): Do not overflow the buffer
+ with the terminating NUL when the argument to be stringified
+ has no tokens.
+
+2002-09-26 David S. Miller <davem@redhat.com>
+
+ PR optimization/7335
+ * calls.c (emit_library_call_value_1): Passing args by reference
+ converts a CONST function into a PURE one.
+
+2002-09-26 Richard Henderson <rth@redhat.com>
+
+ PR c/7160
+ * sched-deps.c (sched_analyze_insn): Make clobber insns depend
+ on call insns.
+
+2002-09-27 Alan Modra <amodra@bigpond.net.au>
+
+ * doloop.c (doloop_modify_runtime <biv skips initial incr>): Adjust
+ by absolute loop increment, not loop increment.
+
+2002-09-25 David S. Miller <davem@redhat.com>
+
+ PR target/7842
+ * config/sparc/sparc.c (set_extends): SImode ASHIFT does not
+ extend.
+
+2002-09-20 Jeroen Dobbelaere <jeroen.dobbelaere@acunia.com>
+
+ * config/arm/arm.md (sign_extract_onebit, not_signextract_onebit):
+ Add clobber of the condition code register.
+
+2002-09-18 Richard Earnshaw (rearnsha@arm.com)
+
+ PR optimization/7967
+ * arm.md (ne_zeroextractsi): Add clobber of the condition code
+ register.
+
+2002-09-17 Richard Henderson <rth@redhat.com>
+
+ * sibcall.c (optimize_sibling_and_tail_recursive_call): Also remove
+ RTX_UNCHANGING_P markers for successful tail-recursive replacement.
+
+2002-09-16 Richard Henderson <rth@redhat.com>
+
+ PR opt/7515
+ * c-objc-common.c (c_cannot_inline_tree_fn): Don't auto-inline
+ functions that don't bind locally.
+
+2002-09-17 Alan Modra <amodra@bigpond.net.au>
+
+ Merge from mainline.
+ 2002-07-20 Alan Modra <amodra@bigpond.net.au>
+ PR optimization/7130
+ * loop.h (struct loop_info): Add "preconditioned".
+ * unroll.c (unroll_loop): Set it.
+ * doloop.c (doloop_modify_runtime): Correct count for unrolled loops.
+
+ 2002-06-24 Alan Modra <amodra@bigpond.net.au>
+ PR optimization/6984
+ * doloop.c (doloop_valid_p): Correct comment.
+ (doloop_modify_runtime <abs_inc != 1>): Simplify.
+ (doloop_modify_runtime <do-while>): Don't emit code when NE.
+
+2002-09-16 Jeff Law <law@redhat.com>
+
+ * libgcc2.c: Do not include machmode.h.
+
+2002-09-16 Jason Merrill <jason@redhat.com>
+ Danny Smith <dannysmith@users.sourceforge.net>
+
+ * config/i386/winnt.c (ix86_handle_dll_attribute): Set
+ DECL_EXTERN and TREE_PUBLIC for dllimported variables here...
+ (i386_pe_mark_dllimport): Not here.
+
2002-09-14 Stephane Carrez <stcarrez@nerim.fr>
* config/m68hc11/m68hc11.md ("movdi_internal"): Allow any offsetable
@@ -185,7 +517,7 @@
2002-08-27 Mark Mitchell <mark@codesourcery.com>
* doc/invoke.texi: Document -Wabi.
-
+
2002-08-23 David Edelsohn <edelsohn@gnu.org>
* config/rs6000/rs6000.c (rs6000_select_section): Treat
@@ -201,7 +533,7 @@
* explow.c (expr_size): Call it.
(int_expr_size): New fn.
* expr.h: Declare it.
- * expr.c (expand_expr) [CONSTRUCTOR]: Use it to calculate how
+ * expr.c (expand_expr) [CONSTRUCTOR]: Use it to calculate how
much to store.
2002-08-23 Alan Modra <amodra@bigpond.net.au>
diff --git a/contrib/gcc/c-objc-common.c b/contrib/gcc/c-objc-common.c
index 0ed3869..43ec820 100644
--- a/contrib/gcc/c-objc-common.c
+++ b/contrib/gcc/c-objc-common.c
@@ -149,6 +149,14 @@ c_cannot_inline_tree_fn (fnp)
&& lookup_attribute ("always_inline", DECL_ATTRIBUTES (fn)) == NULL)
return 1;
+ /* Don't auto-inline anything that might not be bound within
+ this unit of translation. */
+ if (!DECL_DECLARED_INLINE_P (fn) && flag_pic && TREE_PUBLIC (fn))
+ {
+ DECL_UNINLINABLE (fn) = 1;
+ return 1;
+ }
+
if (! function_attribute_inlinable_p (fn))
{
DECL_UNINLINABLE (fn) = 1;
diff --git a/contrib/gcc/calls.c b/contrib/gcc/calls.c
index c0a73e7..449c933 100644
--- a/contrib/gcc/calls.c
+++ b/contrib/gcc/calls.c
@@ -3666,6 +3666,14 @@ emit_library_call_value_1 (retval, orgfun, value, fn_type, outmode, nargs, p)
#endif
;
+ /* If this was a CONST function, it is now PURE since
+ it now reads memory. */
+ if (flags & ECF_CONST)
+ {
+ flags &= ~ECF_CONST;
+ flags |= ECF_PURE;
+ }
+
if (GET_MODE (val) == MEM && ! must_copy)
slot = val;
else if (must_copy)
diff --git a/contrib/gcc/config/arm/arm.h b/contrib/gcc/config/arm/arm.h
index 5e8b5d9..c5431b5 100644
--- a/contrib/gcc/config/arm/arm.h
+++ b/contrib/gcc/config/arm/arm.h
@@ -1093,14 +1093,16 @@ enum reg_class
/* The class value for index registers, and the one for base regs. */
#define INDEX_REG_CLASS (TARGET_THUMB ? LO_REGS : GENERAL_REGS)
-#define BASE_REG_CLASS (TARGET_THUMB ? BASE_REGS : GENERAL_REGS)
+#define BASE_REG_CLASS (TARGET_THUMB ? LO_REGS : GENERAL_REGS)
-/* For the Thumb the high registers cannot be used as base
- registers when addressing quanitities in QI or HI mode. */
+/* For the Thumb the high registers cannot be used as base registers
+ when addressing quanitities in QI or HI mode; if we don't know the
+ mode, then we must be conservative. After reload we must also be
+ conservative, since we can't support SP+reg addressing, and we
+ can't fix up any bad substitutions. */
#define MODE_BASE_REG_CLASS(MODE) \
- (TARGET_ARM ? BASE_REGS : \
- (((MODE) == QImode || (MODE) == HImode || (MODE) == VOIDmode) \
- ? LO_REGS : BASE_REGS))
+ (TARGET_ARM ? GENERAL_REGS : \
+ (((MODE) == SImode && !reload_completed) ? BASE_REGS : LO_REGS))
/* When SMALL_REGISTER_CLASSES is nonzero, the compiler allows
registers explicitly used in the rtl to be used as spill registers
diff --git a/contrib/gcc/config/arm/arm.md b/contrib/gcc/config/arm/arm.md
index b901504..5180c75 100644
--- a/contrib/gcc/config/arm/arm.md
+++ b/contrib/gcc/config/arm/arm.md
@@ -1837,7 +1837,8 @@
(match_operand:SI 1 "s_register_operand" "r")
(match_operand:SI 2 "const_int_operand" "n")
(match_operand:SI 3 "const_int_operand" "n"))
- (const_int 0)))]
+ (const_int 0)))
+ (clobber (reg:CC CC_REGNUM))]
"TARGET_ARM
&& (INTVAL (operands[3]) >= 0 && INTVAL (operands[3]) < 32
&& INTVAL (operands[2]) > 0
@@ -8947,7 +8948,8 @@
[(set (match_operand:SI 0 "s_register_operand" "=r")
(sign_extract:SI (match_operand:SI 1 "s_register_operand" "r")
(const_int 1)
- (match_operand:SI 2 "const_int_operand" "n")))]
+ (match_operand:SI 2 "const_int_operand" "n")))
+ (clobber (reg:CC CC_REGNUM))]
"TARGET_ARM"
"*
operands[2] = GEN_INT (1 << INTVAL (operands[2]));
@@ -8963,7 +8965,8 @@
(not:SI
(sign_extract:SI (match_operand:SI 1 "s_register_operand" "r")
(const_int 1)
- (match_operand:SI 2 "const_int_operand" "n"))))]
+ (match_operand:SI 2 "const_int_operand" "n"))))
+ (clobber (reg:CC CC_REGNUM))]
"TARGET_ARM"
"*
operands[2] = GEN_INT (1 << INTVAL (operands[2]));
diff --git a/contrib/gcc/config/i386/linux64.h b/contrib/gcc/config/i386/linux64.h
index 6158431..8a0bfbe 100644
--- a/contrib/gcc/config/i386/linux64.h
+++ b/contrib/gcc/config/i386/linux64.h
@@ -50,21 +50,14 @@ Boston, MA 02111-1307, USA. */
#undef STARTFILE_SPEC
#define STARTFILE_SPEC \
- "%{m32:%{!shared: \
- %{pg:gcrt1.o%s} %{!pg:%{p:gcrt1.o%s} \
- %{!p:%{profile:gcrt1.o%s} %{!profile:crt1.o%s}}}} \
- crti.o%s %{static:crtbeginT.o%s}\
- %{!static:%{!shared:crtbegin.o%s} %{shared:crtbeginS.o%s}}} \
- %{!m32:%{!shared: \
- %{pg:/usr/lib64/gcrt1.o%s} %{!pg:%{p:/usr/lib64/gcrt1.o%s} \
- %{!p:%{profile:/usr/lib64/gcrt1.o%s} %{!profile:/usr/lib64/crt1.o%s}}}}\
- /usr/lib64/crti.o%s %{static:crtbeginT.o%s} \
- %{!static:%{!shared:crtbegin.o%s} %{shared:crtbeginS.o%s}}}"
+ "%{!shared: \
+ %{pg:gcrt1.o%s} %{!pg:%{p:gcrt1.o%s} \
+ %{!p:%{profile:gcrt1.o%s} %{!profile:crt1.o%s}}}} \
+ crti.o%s %{static:crtbeginT.o%s} \
+ %{!static:%{!shared:crtbegin.o%s} %{shared:crtbeginS.o%s}}"
#undef ENDFILE_SPEC
-#define ENDFILE_SPEC "\
- %{m32:%{!shared:crtend.o%s} %{shared:crtendS.o%s} crtn.o%s} \
- %{!m32:%{!shared:crtend.o%s} %{shared:crtendS.o%s} /usr/lib64/crtn.o%s}"
+#define ENDFILE_SPEC "%{!shared:crtend.o%s} %{shared:crtendS.o%s} crtn.o%s"
#define MULTILIB_DEFAULTS { "m64" }
diff --git a/contrib/gcc/config/i386/t-linux64 b/contrib/gcc/config/i386/t-linux64
index 46a7caa..31b6ad4 100644
--- a/contrib/gcc/config/i386/t-linux64
+++ b/contrib/gcc/config/i386/t-linux64
@@ -6,10 +6,9 @@ SHLIB_MAPFILES = $(srcdir)/libgcc-std.ver \
MULTILIB_OPTIONS = m64/m32
MULTILIB_DIRNAMES = 64 32
+MULTILIB_OSDIRNAMES = ../lib64 ../lib
LIBGCC = stmp-multilib
INSTALL_LIBGCC = install-multilib
EXTRA_MULTILIB_PARTS=crtbegin.o crtend.o crtbeginS.o crtendS.o crtbeginT.o
-
-SHLIB_SLIBDIR_SUFFIXES = 64:64 32:
diff --git a/contrib/gcc/config/i386/winnt.c b/contrib/gcc/config/i386/winnt.c
index 9d955df..6928a8c 100644
--- a/contrib/gcc/config/i386/winnt.c
+++ b/contrib/gcc/config/i386/winnt.c
@@ -76,6 +76,15 @@ ix86_handle_dll_attribute (node, name, args, flags, no_add_attrs)
}
}
+ /* `extern' needn't be specified with dllimport.
+ Specify `extern' now and hope for the best. Sigh. */
+ else if (TREE_CODE (*node) == VAR_DECL
+ && is_attribute_p ("dllimport", name))
+ {
+ DECL_EXTERNAL (*node) = 1;
+ TREE_PUBLIC (*node) = 1;
+ }
+
return NULL_TREE;
}
@@ -300,16 +309,6 @@ i386_pe_mark_dllimport (decl)
return;
}
- /* `extern' needn't be specified with dllimport.
- Specify `extern' now and hope for the best. Sigh. */
- if (TREE_CODE (decl) == VAR_DECL
- /* ??? Is this test for vtables needed? */
- && !DECL_VIRTUAL_P (decl))
- {
- DECL_EXTERNAL (decl) = 1;
- TREE_PUBLIC (decl) = 1;
- }
-
newname = alloca (strlen (oldname) + 11);
sprintf (newname, "@i._imp__%s", oldname);
diff --git a/contrib/gcc/config/rs6000/rs6000.md b/contrib/gcc/config/rs6000/rs6000.md
index f032bfd..6e86d73 100644
--- a/contrib/gcc/config/rs6000/rs6000.md
+++ b/contrib/gcc/config/rs6000/rs6000.md
@@ -9657,7 +9657,7 @@
(define_insn "load_toc_v4_PIC_2"
[(set (match_operand:SI 0 "register_operand" "=r")
- (mem:SI (plus:SI (match_operand:SI 1 "register_operand" "r")
+ (mem:SI (plus:SI (match_operand:SI 1 "register_operand" "b")
(minus:SI (match_operand:SI 2 "immediate_operand" "s")
(match_operand:SI 3 "immediate_operand" "s")))))]
"TARGET_ELF && DEFAULT_ABI != ABI_AIX && flag_pic == 2"
diff --git a/contrib/gcc/config/sparc/linux64.h b/contrib/gcc/config/sparc/linux64.h
index 1dfd97f..c7d8f491 100644
--- a/contrib/gcc/config/sparc/linux64.h
+++ b/contrib/gcc/config/sparc/linux64.h
@@ -1,5 +1,5 @@
/* Definitions for 64-bit SPARC running Linux-based GNU systems with ELF.
- Copyright 1996, 1997, 1998, 2000 Free Software Foundation, Inc.
+ Copyright 1996, 1997, 1998, 2000, 2002 Free Software Foundation, Inc.
Contributed by David S. Miller (davem@caip.rutgers.edu)
This file is part of GNU CC.
@@ -56,38 +56,12 @@ Boston, MA 02111-1307, USA. */
#undef STARTFILE_SPEC
-#define STARTFILE_SPEC32 \
+#define STARTFILE_SPEC \
"%{!shared: \
- %{pg:/usr/lib/gcrt1.o%s} %{!pg:%{p:/usr/lib/gcrt1.o%s} %{!p:/usr/lib/crt1.o%s}}}\
- /usr/lib/crti.o%s %{static:crtbeginT.o%s}\
+ %{pg:gcrt1.o%s} %{!pg:%{p:gcrt1.o%s} %{!p:crt1.o%s}}}\
+ crti.o%s %{static:crtbeginT.o%s}\
%{!static:%{!shared:crtbegin.o%s} %{shared:crtbeginS.o%s}}"
-#define STARTFILE_SPEC64 \
- "%{!shared: \
- %{pg:/usr/lib64/gcrt1.o%s} %{!pg:%{p:/usr/lib64/gcrt1.o%s} %{!p:/usr/lib64/crt1.o%s}}}\
- /usr/lib64/crti.o%s %{static:crtbeginT.o%s}\
- %{!static:%{!shared:crtbegin.o%s} %{shared:crtbeginS.o%s}}"
-
-#ifdef SPARC_BI_ARCH
-
-#if DEFAULT_ARCH32_P
-#define STARTFILE_SPEC "\
-%{m32:" STARTFILE_SPEC32 "} \
-%{m64:" STARTFILE_SPEC64 "} \
-%{!m32:%{!m64:" STARTFILE_SPEC32 "}}"
-#else
-#define STARTFILE_SPEC "\
-%{m32:" STARTFILE_SPEC32 "} \
-%{m64:" STARTFILE_SPEC64 "} \
-%{!m32:%{!m64:" STARTFILE_SPEC64 "}}"
-#endif
-
-#else
-
-#define STARTFILE_SPEC STARTFILE_SPEC64
-
-#endif
-
/* Provide a ENDFILE_SPEC appropriate for GNU/Linux. Here we tack on
the GNU/Linux magical crtend.o file (see crtstuff.c) which
provides part of the support for getting C++ file-scope static
@@ -96,36 +70,9 @@ Boston, MA 02111-1307, USA. */
#undef ENDFILE_SPEC
-#define ENDFILE_SPEC32 \
- "%{!shared:crtend.o%s} %{shared:crtendS.o%s} /usr/lib/crtn.o%s"
-
-#define ENDFILE_SPEC64 \
- "%{!shared:crtend.o%s} %{shared:crtendS.o%s} /usr/lib64/crtn.o%s"
-
-#define ENDFILE_SPEC_COMMON \
- "%{ffast-math|funsafe-math-optimizations:crtfastmath.o%s}"
-
-#ifdef SPARC_BI_ARCH
-
-#if DEFAULT_ARCH32_P
-#define ENDFILE_SPEC "\
-%{m32:" ENDFILE_SPEC32 "} \
-%{m64:" ENDFILE_SPEC64 "} \
-%{!m32:%{!m64:" ENDFILE_SPEC32 "}} " \
-ENDFILE_SPEC_COMMON
-#else
-#define ENDFILE_SPEC "\
-%{m32:" ENDFILE_SPEC32 "} \
-%{m64:" ENDFILE_SPEC64 "} \
-%{!m32:%{!m64:" ENDFILE_SPEC64 "}} " \
-ENDFILE_SPEC_COMMON
-#endif
-
-#else
-
-#define ENDFILE_SPEC ENDFILE_SPEC64 " " ENDFILE_SPEC_COMMON
-
-#endif
+#define ENDFILE_SPEC \
+ "%{!shared:crtend.o%s} %{shared:crtendS.o%s} crtn.o%s\
+ %{ffast-math|funsafe-math-optimizations:crtfastmath.o%s}"
/* The GNU C++ standard library requires that these macros be defined. */
#undef CPLUSPLUS_CPP_SPEC
diff --git a/contrib/gcc/config/sparc/sol2-bi.h b/contrib/gcc/config/sparc/sol2-bi.h
index 9828d63..e19e888 100644
--- a/contrib/gcc/config/sparc/sol2-bi.h
+++ b/contrib/gcc/config/sparc/sol2-bi.h
@@ -72,30 +72,6 @@
%{!mcpu*:%(asm_cpu_default)} \
"
-#define STARTFILE_SPEC32 "\
-%{ansi:values-Xc.o%s} \
-%{!ansi: \
- %{traditional:values-Xt.o%s} \
- %{!traditional:values-Xa.o%s}}"
-
-#define STARTFILE_SPEC64 "\
-%{ansi:/usr/lib/sparcv9/values-Xc.o%s} \
-%{!ansi: \
- %{traditional:/usr/lib/sparcv9/values-Xt.o%s} \
- %{!traditional:/usr/lib/sparcv9/values-Xa.o%s}}"
-
-#if DEFAULT_ARCH32_P
-#define STARTFILE_ARCH_SPEC "\
-%{m32:" STARTFILE_SPEC32 "} \
-%{m64:" STARTFILE_SPEC64 "} \
-%{!m32:%{!m64:" STARTFILE_SPEC32 "}}"
-#else
-#define STARTFILE_ARCH_SPEC "\
-%{m32:" STARTFILE_SPEC32 "} \
-%{m64:" STARTFILE_SPEC64 "} \
-%{!m32:%{!m64:" STARTFILE_SPEC64 "}}"
-#endif
-
#undef STARTFILE_SPEC
#define STARTFILE_SPEC "%{!shared: \
%{!symbolic: \
@@ -103,7 +79,10 @@
%{!p: \
%{pg:gcrt1.o%s gmon.o%s} \
%{!pg:crt1.o%s}}}} \
- crti.o%s " STARTFILE_ARCH_SPEC " \
+ crti.o%s \
+ %{ansi:values-Xc.o%s} \
+ %{!ansi: %{traditional:values-Xt.o%s} \
+ %{!traditional:values-Xa.o%s}} \
crtbegin.o%s"
#undef CPP_CPU_DEFAULT_SPEC
diff --git a/contrib/gcc/config/sparc/sparc.c b/contrib/gcc/config/sparc/sparc.c
index 6ef28141c..c23cbef 100644
--- a/contrib/gcc/config/sparc/sparc.c
+++ b/contrib/gcc/config/sparc/sparc.c
@@ -8650,7 +8650,6 @@ set_extends (insn)
return INTVAL (op1) >= 0;
return (GET_CODE (op1) == REG && sparc_check_64 (op1, insn) == 1);
}
- case ASHIFT:
case LSHIFTRT:
return GET_MODE (SET_SRC (pat)) == SImode;
/* Positive integers leave the high bits zero. */
diff --git a/contrib/gcc/config/sparc/sparc.md b/contrib/gcc/config/sparc/sparc.md
index ebb6768..746dc72 100644
--- a/contrib/gcc/config/sparc/sparc.md
+++ b/contrib/gcc/config/sparc/sparc.md
@@ -2517,7 +2517,7 @@
;
}")
-;; Be careful, fmovd does not exist when !arch64.
+;; Be careful, fmovd does not exist when !v9.
;; We match MEM moves directly when we have correct even
;; numbered registers, but fall into splits otherwise.
;; The constraint ordering here is really important to
@@ -2531,9 +2531,9 @@
(define_insn "*movdi_insn_sp32_v9"
[(set (match_operand:DI 0 "nonimmediate_operand"
- "=T,o,T,U,o,r,r,r,?T,?f,?f,?o,?f")
+ "=T,o,T,U,o,r,r,r,?T,?f,?f,?o,?f,?e,?e,?W")
(match_operand:DI 1 "input_operand"
- " J,J,U,T,r,o,i,r, f, T, o, f, f"))]
+ " J,J,U,T,r,o,i,r, f, T, o, f, f, e, W, e"))]
"! TARGET_ARCH64 && TARGET_V9
&& (GET_CODE (operands[0]) != MEM || GET_CODE (operands[1]) != MEM)"
"@
@@ -2549,9 +2549,13 @@
ldd\\t%1, %0
#
#
- #"
- [(set_attr "type" "store,store,store,load,*,*,*,*,fpstore,fpload,*,*,*")
- (set_attr "length" "*,2,*,*,2,2,2,2,*,*,2,2,2")])
+ #
+ fmovd\\t%1, %0
+ ldd\\t%1, %0
+ std\\t%1, %0"
+ [(set_attr "type" "store,store,store,load,*,*,*,*,fpstore,fpload,*,*,*,fpmove,fpload,fpstore")
+ (set_attr "length" "*,2,*,*,2,2,2,2,*,*,2,2,2,*,*,*")
+ (set_attr "fptype" "*,*,*,*,*,*,*,*,*,*,*,*,*,double,*,*")])
(define_insn "*movdi_insn_sp32"
[(set (match_operand:DI 0 "nonimmediate_operand"
@@ -2861,7 +2865,14 @@
(define_split
[(set (match_operand:DI 0 "register_operand" "")
(match_operand:DI 1 "const_double_operand" ""))]
- "! TARGET_ARCH64 && reload_completed"
+ "reload_completed
+ && (! TARGET_V9
+ || (! TARGET_ARCH64
+ && ((GET_CODE (operands[0]) == REG
+ && REGNO (operands[0]) < 32)
+ || (GET_CODE (operands[0]) == SUBREG
+ && GET_CODE (SUBREG_REG (operands[0])) == REG
+ && REGNO (SUBREG_REG (operands[0])) < 32))))"
[(clobber (const_int 0))]
"
{
diff --git a/contrib/gcc/config/sparc/t-linux64 b/contrib/gcc/config/sparc/t-linux64
index a648626..3e3fa4c 100644
--- a/contrib/gcc/config/sparc/t-linux64
+++ b/contrib/gcc/config/sparc/t-linux64
@@ -1,8 +1,6 @@
-MULTILIB_OPTIONS = m64/m32 mno-app-regs|mcmodel=medany
-MULTILIB_DIRNAMES = 64 32 alt
-MULTILIB_MATCHES = mcmodel?medany=mcmodel?medmid
-MULTILIB_EXCEPTIONS = m32/mno-app-regs* m32/mcmodel=*
-MULTILIB_EXCLUSIONS = m32/!m64/mno-app-regs m32/!m64/mcmodel=medany
+MULTILIB_OPTIONS = m64/m32
+MULTILIB_DIRNAMES = 64 32
+MULTILIB_OSDIRNAMES = ../lib64 ../lib
LIBGCC = stmp-multilib
INSTALL_LIBGCC = install-multilib
@@ -10,10 +8,12 @@ INSTALL_LIBGCC = install-multilib
EXTRA_MULTILIB_PARTS=crtbegin.o crtend.o crtbeginS.o crtendS.o crtbeginT.o \
crtfastmath.o
-SHLIB_SLIBDIR_SUFFIXES = 64:64 32:
-
# Override t-slibgcc-elf-ver to export some libgcc symbols with
# the symbol versions that glibc used.
# Avoid the t-linux version file.
SHLIB_MAPFILES = $(srcdir)/libgcc-std.ver \
$(srcdir)/config/sparc/libgcc-sparc-glibc.ver
+
+CRTSTUFF_T_CFLAGS = `if test x$$($(GCC_FOR_TARGET) $(MULTILIB_CFLAGS) \
+ -print-multi-os-directory) \
+ = x../lib64; then echo -mcmodel=medany; fi`
diff --git a/contrib/gcc/config/sparc/t-sol2-64 b/contrib/gcc/config/sparc/t-sol2-64
index 39204d7..3c15f0a 100644
--- a/contrib/gcc/config/sparc/t-sol2-64
+++ b/contrib/gcc/config/sparc/t-sol2-64
@@ -1,11 +1,10 @@
MULTILIB_OPTIONS = m32/m64
MULTILIB_DIRNAMES = sparcv7 sparcv9
MULTILIB_MATCHES =
+MULTILIB_OSDIRNAMES = . sparcv9
LIBGCC = stmp-multilib
INSTALL_LIBGCC = install-multilib
EXTRA_MULTILIB_PARTS=crtbegin.o crtend.o gmon.o crt1.o crti.o crtn.o gcrt1.o \
crtfastmath.o
-
-SHLIB_SLIBDIR_SUFFIXES = sparcv9:/sparcv9 sparcv7:
diff --git a/contrib/gcc/cp/ChangeLog b/contrib/gcc/cp/ChangeLog
index f75f91f..cc84a03 100644
--- a/contrib/gcc/cp/ChangeLog
+++ b/contrib/gcc/cp/ChangeLog
@@ -1,3 +1,54 @@
+2002-10-09 Zack Weinberg <zack@codesourcery.com>
+
+ PR c/7353
+ * decl.c (start_decl): Unconditionally issue error for
+ 'typedef foo = bar'.
+ (cp_finish_decl): Remove special case for TYPE_DECL with initializer.
+ (grokdeclarator): Remove redundant error for 'typedef foo = bar'.
+
+2002-10-03 Mark Mitchell <mark@codesourcery.com>
+
+ PR c++/7754
+ * decl2.c (finish_anon_union): Do not expand anonymous unions when
+ procesing template functions.
+ * pt.c (tsubst_decl, case VAR_DECL): Try to complete the variable
+ type. Call layout_decl.
+ (tsubst_expr, case DECL_STMT): Handle anonymous unions.
+
+2002-10-07 Richard Henderson <rth@redhat.com>
+
+ * decl2.c: Complete reversion of c++/7754.
+
+2002-10-06 Roger Sayle <roger@eyesopen.com>
+
+ PR optimization/6627
+ * cp/cp-tree.h (enum ptrmemfunc_vbit_where_t): Delete definition
+ from here, and move it to tree.h.
+ * cp/decl.c (cxx_init_decl_processing): If storing the vbit
+ in function pointers, ensure that force_align_functions_log
+ is atleast one.
+
+2002-10-04 H.J. Lu (hjl@gnu.org)
+
+ * pt.c (tsubst_decl, case VAR_DECL): Back out the last change.
+ (tsubst_expr, case DECL_STMT): Likewise.
+
+2002-10-02 Mark Mitchell <mark@codesourcery.com>
+
+ PR c++/7754
+ * decl2.c (finish_anon_union): Do not expand anonymous unions when
+ procesing template functions.
+ * pt.c (tsubst_decl, case VAR_DECL): Try to complete the variable
+ type. Call layout_decl.
+ (tsubst_expr, case DECL_STMT): Handle anonymous unions.
+
+2002-10-02 Mark Mitchell <mark@codesourcery.com>
+
+ PR c++/7188.
+ * init.c (expand_member_init): Allow a FIELD_DECL to be passed in
+ directly.
+ * pt.c (tsubst_initializer_list): Use expand_member_init.
+
2002-09-04 Jakub Jelinek <jakub@redhat.com>
* decl.c (start_cleanup_fn): Clear interface_only before
@@ -336,7 +387,7 @@
2002-04-29 Nathan Sidwell <nathan@codesourcery.com>
PR c++/5719
- * decl.c (grok_op_properties): Assignment ops don't have to return
+ * decl.c (grok_op_properties): Assignment ops don't have to return
by value. operator% should.
2002-04-28 Franz Sirl <Franz.Sirl-kernel@lauterbach.com>
@@ -420,7 +471,7 @@
(finish_init_stmts): Set STMT_EXPR_NO_SCOPE.
* semantics.c (begin_gobal_stmt_expr): Adjust call to
expand_start_stmt_expr.
-
+
2002-04-15 Mark Mitchell <mark@codesourcery.com>
* decl.c (register_dtor_fn): Pass the address of dso_handle, not
@@ -449,11 +500,11 @@
* typeck.c (type_after_usual_arithmetic_conversions):
If two types have the same variant, return immediately.
- When two floating-point operands are the same precision:
+ When two floating-point operands are the same precision:
convert to float if one of the operands is float;
if neither operand is one of the standard types, return the type
of the first operand.
-
+
2002-04-12 Richard Sandiford <rsandifo@redhat.com>
* decl.c (duplicate_decls): Don't try to unify an implicit typedef
@@ -511,7 +562,7 @@
set before checking it.
PR c++/6179
- * method.c (implicitly_declare_fn): Pass unqualified type to
+ * method.c (implicitly_declare_fn): Pass unqualified type to
synthesize_exception_spec.
2002-04-03 Jason Merrill <jason@redhat.com>
@@ -576,7 +627,7 @@
PR c++/4884
* call.c (build_op_delete_call): Allow for the fact the placement
may be a COMPOUND_EXPR.
-
+
2002-03-26 Nathan Sidwell <nathan@codesourcery.com>
PR c++/5682
@@ -630,7 +681,7 @@
2002-03-18 Ashif Harji <asharji@uwaterloo.ca>
- * lang-specs.h (compiler default_compilers): Add
+ * lang-specs.h (compiler default_compilers): Add
-no-integrated-cpp flag to invoke an external cpp.
2002-03-18 Jason Merrill <jason@redhat.com>
@@ -747,7 +798,7 @@
with pointer to member conversions.
2002-03-08 Craig Rodrigues <rodrigc@gcc.gnu.org>
-
+
* cp-tree.h (CLEAR_BINFO_MARKED): Make both parts of
conditional return void.
@@ -781,7 +832,7 @@
* decl.c (finish_function): Only warn about missing return
statement with -Wreturn-type.
-2002-02-24 Craig Rodrigues <rodrigc@gcc.gnu.org>
+2002-02-24 Craig Rodrigues <rodrigc@gcc.gnu.org>
PR c++/4093
* cp-tree.h (SET_BINFO_MARKED): Cast false part of condition
@@ -835,7 +886,7 @@
2002-02-19 Jason Merrill <jason@redhat.com>
- ABI change: Mangle `void (A::*)() const' as
+ ABI change: Mangle `void (A::*)() const' as
M1AKFvvE, not MK1AFvvE.
* mangle.c (write_function_type): Write cv-quals for member
function type here.
@@ -910,14 +961,14 @@
(coerce_template_template_parms, convert_template_argument,
coerce_template_parms, maybe_get_template_decl_from_type_decl,
lookup_template_class, tsubst_friend_function, tsubst_friend_class,
- instantiate_class_template, tsubst_template_arg_vector,
- tsubst_template_parms, tsubst_aggr_type, tsubst_default_argument,
+ instantiate_class_template, tsubst_template_arg_vector,
+ tsubst_template_parms, tsubst_aggr_type, tsubst_default_argument,
tsubst_decl, tsubst_arg_types, tsubst_function_type,
- tsubst_call_declarator_parms, tsubst, tsubst_copy, tsubst_expr,
+ tsubst_call_declarator_parms, tsubst, tsubst_copy, tsubst_expr,
instantiate_template, fn_type_unification,
- resolve_overloaded_unification, verify_class_unification,
- unify, get_bindings_real, do_type_instantiation,
- regenerate_decl_from_template, instantiate_decl,
+ resolve_overloaded_unification, verify_class_unification,
+ unify, get_bindings_real, do_type_instantiation,
+ regenerate_decl_from_template, instantiate_decl,
tsubst_initializer_list, tsubst_enum,
get_mostly_instantiated_function_type,
invalid_nontype_parm_type_p): Likewise.
@@ -978,7 +1029,7 @@
2002-02-01 Jason Merrill <jason@redhat.com>
PR c++/4872
- * decl.c (finish_function): Warn about a non-void function with
+ * decl.c (finish_function): Warn about a non-void function with
no return statement and no abnormal exit.
* cp-tree.h (struct cp_language_function): Add returns_abnormally.
(current_function_returns_abnormally): New macro.
diff --git a/contrib/gcc/cp/cp-tree.h b/contrib/gcc/cp/cp-tree.h
index 787114f..4bd0879 100644
--- a/contrib/gcc/cp/cp-tree.h
+++ b/contrib/gcc/cp/cp-tree.h
@@ -2557,32 +2557,6 @@ extern int flag_new_for_scope;
member function. [expr.unary.op]/3 */
#define PTRMEM_OK_P(NODE) TREE_LANG_FLAG_0 (NODE)
-/* A pointer-to-function member type looks like:
-
- struct {
- __P __pfn;
- ptrdiff_t __delta;
- };
-
- If __pfn is NULL, it is a NULL pointer-to-member-function.
-
- (Because the vtable is always the first thing in the object, we
- don't need its offset.) If the function is virtual, then PFN is
- one plus twice the index into the vtable; otherwise, it is just a
- pointer to the function.
-
- Unfortunately, using the lowest bit of PFN doesn't work in
- architectures that don't impose alignment requirements on function
- addresses, or that use the lowest bit to tell one ISA from another,
- for example. For such architectures, we use the lowest bit of
- DELTA instead of the lowest bit of the PFN, and DELTA will be
- multiplied by 2. */
-enum ptrmemfunc_vbit_where_t
-{
- ptrmemfunc_vbit_in_pfn,
- ptrmemfunc_vbit_in_delta
-};
-
/* Get the POINTER_TYPE to the METHOD_TYPE associated with this
pointer to member function. TYPE_PTRMEMFUNC_P _must_ be true,
before using this macro. */
diff --git a/contrib/gcc/cp/decl2.c b/contrib/gcc/cp/decl2.c
index 0eb4799..4334963 100644
--- a/contrib/gcc/cp/decl2.c
+++ b/contrib/gcc/cp/decl2.c
@@ -1975,26 +1975,31 @@ finish_anon_union (anon_union_decl)
return;
}
- main_decl = build_anon_union_vars (anon_union_decl,
- &DECL_ANON_UNION_ELEMS (anon_union_decl),
- static_p, external_p);
-
- if (main_decl == NULL_TREE)
+ if (!processing_template_decl)
{
- warning ("anonymous aggregate with no members");
- return;
- }
+ main_decl
+ = build_anon_union_vars (anon_union_decl,
+ &DECL_ANON_UNION_ELEMS (anon_union_decl),
+ static_p, external_p);
+
+ if (main_decl == NULL_TREE)
+ {
+ warning ("anonymous aggregate with no members");
+ return;
+ }
- if (static_p)
- {
- make_decl_rtl (main_decl, 0);
- COPY_DECL_RTL (main_decl, anon_union_decl);
- expand_anon_union_decl (anon_union_decl,
- NULL_TREE,
- DECL_ANON_UNION_ELEMS (anon_union_decl));
+ if (static_p)
+ {
+ make_decl_rtl (main_decl, 0);
+ COPY_DECL_RTL (main_decl, anon_union_decl);
+ expand_anon_union_decl (anon_union_decl,
+ NULL_TREE,
+ DECL_ANON_UNION_ELEMS (anon_union_decl));
+ return;
+ }
}
- else
- add_decl_stmt (anon_union_decl);
+
+ add_decl_stmt (anon_union_decl);
}
/* Finish processing a builtin type TYPE. It's name is NAME,
diff --git a/contrib/gcc/cp/init.c b/contrib/gcc/cp/init.c
index 369e511..a46d853 100644
--- a/contrib/gcc/cp/init.c
+++ b/contrib/gcc/cp/init.c
@@ -1094,7 +1094,10 @@ expand_member_init (exp, name, init)
}
else
{
- field = lookup_field (type, name, 1, 0);
+ if (TREE_CODE (name) == IDENTIFIER_NODE)
+ field = lookup_field (type, name, 1, 0);
+ else
+ field = name;
if (! member_init_ok_or_else (field, type, name))
return NULL_TREE;
diff --git a/contrib/gcc/cp/pt.c b/contrib/gcc/cp/pt.c
index 2180e4b..8fc9f74 100644
--- a/contrib/gcc/cp/pt.c
+++ b/contrib/gcc/cp/pt.c
@@ -6079,6 +6079,8 @@ tsubst_decl (t, args, type, complain)
}
r = copy_decl (t);
+ if (TREE_CODE (r) == VAR_DECL)
+ type = complete_type (type);
TREE_TYPE (r) = type;
c_apply_type_quals_to_decl (cp_type_quals (type), r);
DECL_CONTEXT (r) = ctx;
@@ -6115,6 +6117,8 @@ tsubst_decl (t, args, type, complain)
TREE_CHAIN (r) = NULL_TREE;
if (TREE_CODE (r) == VAR_DECL && VOID_TYPE_P (type))
cp_error_at ("instantiation of `%D' as type `%T'", r, type);
+ /* Compute the size, alignment, etc. of R. */
+ layout_decl (r, 0);
}
break;
@@ -7374,9 +7378,6 @@ tsubst_expr (t, args, complain, in_decl)
decl = tsubst (decl, args, complain, in_decl);
if (decl != error_mark_node)
{
- if (TREE_CODE (decl) != TYPE_DECL)
- /* Make sure the type is instantiated now. */
- complete_type (TREE_TYPE (decl));
if (init)
DECL_INITIAL (decl) = error_mark_node;
/* By marking the declaration as instantiated, we avoid
@@ -7386,19 +7387,26 @@ tsubst_expr (t, args, complain, in_decl)
do. */
if (TREE_CODE (decl) == VAR_DECL)
DECL_TEMPLATE_INSTANTIATED (decl) = 1;
- maybe_push_decl (decl);
- if (DECL_PRETTY_FUNCTION_P (decl))
+ if (TREE_CODE (decl) == VAR_DECL
+ && ANON_AGGR_TYPE_P (TREE_TYPE (decl)))
+ /* Anonymous aggregates are a special case. */
+ finish_anon_union (decl);
+ else
{
- /* For __PRETTY_FUNCTION__ we have to adjust the
- initializer. */
- const char *const name
- = (*decl_printable_name) (current_function_decl, 2);
- init = cp_fname_init (name);
- TREE_TYPE (decl) = TREE_TYPE (init);
+ maybe_push_decl (decl);
+ if (DECL_PRETTY_FUNCTION_P (decl))
+ {
+ /* For __PRETTY_FUNCTION__ we have to adjust the
+ initializer. */
+ const char *const name
+ = (*decl_printable_name) (current_function_decl, 2);
+ init = cp_fname_init (name);
+ TREE_TYPE (decl) = TREE_TYPE (init);
+ }
+ else
+ init = tsubst_expr (init, args, complain, in_decl);
+ cp_finish_decl (decl, init, NULL_TREE, 0);
}
- else
- init = tsubst_expr (init, args, complain, in_decl);
- cp_finish_decl (decl, init, NULL_TREE, 0);
}
}
@@ -10274,8 +10282,10 @@ tsubst_initializer_list (t, argvec)
else
init = convert_from_reference (init);
- *p = build_tree_list (decl, init);
- p = &TREE_CHAIN (*p);
+ *p = expand_member_init (current_class_ref, decl,
+ init ? init : void_type_node);
+ if (*p)
+ p = &TREE_CHAIN (*p);
}
return first;
}
diff --git a/contrib/gcc/cpplib.c b/contrib/gcc/cpplib.c
index 096a711..cff9eeb 100644
--- a/contrib/gcc/cpplib.c
+++ b/contrib/gcc/cpplib.c
@@ -1224,6 +1224,9 @@ destringize_and_run (pfile, in)
{
const unsigned char *src, *limit;
char *dest, *result;
+ cpp_context saved_context;
+ cpp_context *saved_cur_context;
+ unsigned int saved_line;
dest = result = alloca (in->len + 1);
for (src = in->text, limit = src + in->len; src < limit;)
@@ -1235,7 +1238,40 @@ destringize_and_run (pfile, in)
}
*dest = '\0';
+ /* FIXME. All this saving is a horrible kludge to handle the case
+ when we're in a macro expansion.
+
+ A better strategy it to not convert _Pragma to #pragma if doing
+ preprocessed output, but to just pass it through as-is, unless it
+ is a CPP pragma in which case is should be processed normally.
+ When compiling the preprocessed output the _Pragma should be
+ handled. This will be become necessary when we move to
+ line-at-a-time lexing since we will be macro-expanding the line
+ before outputting / compiling it. */
+ saved_line = pfile->line;
+ saved_context = pfile->base_context;
+ saved_cur_context = pfile->context;
+ pfile->context = &pfile->base_context;
run_directive (pfile, T_PRAGMA, result, dest - result);
+ pfile->context = saved_cur_context;
+ pfile->base_context = saved_context;
+ pfile->line = saved_line;
+
+ /* See above comment. For the moment, we'd like
+
+ token1 _Pragma ("foo") token2
+
+ to be output as
+
+ token1
+ # 7 "file.c"
+ #pragma foo
+ # 7 "file.c"
+ token2
+
+ Getting the line markers is a little tricky. */
+ if (pfile->cb.line_change)
+ (*pfile->cb.line_change) (pfile, pfile->cur_token, false);
}
/* Handle the _Pragma operator. */
@@ -1245,25 +1281,10 @@ _cpp_do__Pragma (pfile)
{
const cpp_token *string = get__Pragma_string (pfile);
- if (!string)
- cpp_error (pfile, "_Pragma takes a parenthesized string literal");
+ if (string)
+ destringize_and_run (pfile, &string->val.str);
else
- {
- /* Ideally, we'd like
- token1 _Pragma ("foo") token2
- to be output as
- token1
- # 7 "file.c"
- #pragma foo
- # 7 "file.c"
- token2
- Getting these correct line markers is a little tricky. */
-
- unsigned int orig_line = pfile->line;
- destringize_and_run (pfile, &string->val.str);
- pfile->line = orig_line;
- pfile->buffer->saved_flags = BOL;
- }
+ cpp_error (pfile, "_Pragma takes a parenthesized string literal");
}
/* Just ignore #sccs, on systems where we define it at all. */
diff --git a/contrib/gcc/cppmacro.c b/contrib/gcc/cppmacro.c
index c85ac21..70e52fd 100644
--- a/contrib/gcc/cppmacro.c
+++ b/contrib/gcc/cppmacro.c
@@ -348,6 +348,12 @@ stringify_arg (pfile, arg)
}
/* Commit the memory, including NUL, and return the token. */
+ if ((size_t) (BUFF_LIMIT (pfile->u_buff) - dest) < 1)
+ {
+ size_t len_so_far = dest - BUFF_FRONT (pfile->u_buff);
+ _cpp_extend_buff (pfile, &pfile->u_buff, 1);
+ dest = BUFF_FRONT (pfile->u_buff) + len_so_far;
+ }
len = dest - BUFF_FRONT (pfile->u_buff);
BUFF_FRONT (pfile->u_buff) = dest + 1;
return new_string_token (pfile, dest - len, len);
diff --git a/contrib/gcc/doc/cpp.texi b/contrib/gcc/doc/cpp.texi
index 8e829d8..39e6a28 100644
--- a/contrib/gcc/doc/cpp.texi
+++ b/contrib/gcc/doc/cpp.texi
@@ -830,11 +830,22 @@ version of GCC in use.
You can add to this list with the @option{-I@var{dir}} command line
option. All the directories named by @option{-I} are searched, in
-left-to-right order, @emph{before} the default directories. You can
-also prevent GCC from searching any of the default directories with the
-@option{-nostdinc} option. This is useful when you are compiling an
+left-to-right order, @emph{before} the default directories. The only
+exception is when @file{dir} is already searched by default. In
+this case, the option is ignored and the search order for system
+directories remains unchanged.
+
+Duplicate directories are removed from the quote and bracket search
+chains before the two chains are merged to make the final search chain.
+Thus, it is possible for a directory to occur twice in the final search
+chain if it was specified in both the quote and bracket chains.
+
+You can prevent GCC from searching any of the default directories with
+the @option{-nostdinc} option. This is useful when you are compiling an
operating system kernel or some other program that does not use the
standard C library facilities, or the standard C library itself.
+@option{-I} options are not ignored as described above when
+@option{-nostdinc} is in effect.
GCC looks for headers requested with @code{@w{#include "@var{file}"}}
first in the directory containing the current file, then in the same
@@ -843,12 +854,6 @@ For example, if @file{/usr/include/sys/stat.h} contains
@code{@w{#include "types.h"}}, GCC looks for @file{types.h} first in
@file{/usr/include/sys}, then in its usual search path.
-If you name a search directory with @option{-I@var{dir}} that is also a
-system include directory, the @option{-I} wins; the directory will be
-searched according to the @option{-I} ordering, and it will not be
-treated as a system include directory. GCC will warn you when a system
-include directory is hidden in this way.
-
@samp{#line} (@pxref{Line Control}) does not change GCC's idea of the
directory containing the current file.
@@ -1081,8 +1086,8 @@ found in that directory will be considered system headers.
All directories named by @option{-isystem} are searched @emph{after} all
directories named by @option{-I}, no matter what their order was on the
command line. If the same directory is named by both @option{-I} and
-@option{-isystem}, @option{-I} wins; it is as if the @option{-isystem} option
-had never been specified at all. GCC warns you when this happens.
+@option{-isystem}, the @option{-I} option is ignored. GCC provides an
+informative message when this occurs if @option{-v} is used.
@findex #pragma GCC system_header
There is also a directive, @code{@w{#pragma GCC system_header}}, which
@@ -1815,9 +1820,7 @@ conformance to the C Standard. GNU CPP follows the host convention when
processing system header files, but when processing user files
@code{__STDC__} is always 1. This has been reported to cause problems;
for instance, some versions of Solaris provide X Windows headers that
-expect @code{__STDC__} to be either undefined or 1. You may be able to
-work around this sort of problem by using an @option{-I} option to
-cancel treatment of those headers as system headers. @xref{Invocation}.
+expect @code{__STDC__} to be either undefined or 1. @xref{Invocation}.
@item __STDC_VERSION__
This macro expands to the C Standard's version number, a long integer
@@ -3733,9 +3736,9 @@ Here are a few more obsolete features.
@item Attempting to paste two tokens which together do not form a valid
preprocessing token.
-The preprocessor currently warns about this and outputs the two tokens
-adjacently, which is probably the behavior the programmer intends. It
-may not work in future, though.
+The preprocessor currently warns about this, and the resulting
+preprocessed output is undefined. The tokens remain distinct if the
+preprocessor is being used directly by the compiler front end.
Most of the time, when you get this warning, you will find that @samp{##}
is being used superstitiously, to guard against whitespace appearing
diff --git a/contrib/gcc/doc/extend.texi b/contrib/gcc/doc/extend.texi
index 79eea70..281e4ac 100644
--- a/contrib/gcc/doc/extend.texi
+++ b/contrib/gcc/doc/extend.texi
@@ -385,7 +385,6 @@ extensions, accepted by GCC in C89 mode and in C++.
* Labels as Values:: Getting pointers to labels, and computed gotos.
* Nested Functions:: As in Algol and Pascal, lexical scoping of functions.
* Constructing Calls:: Dispatching a call to another function.
-* Naming Types:: Giving a name to the type of some expression.
* Typeof:: @code{typeof}: referring to the type of an expression.
* Lvalues:: Using @samp{?:}, @samp{,} and casts in lvalues.
* Conditionals:: Omitting the middle operand of a @samp{?:} expression.
@@ -495,8 +494,7 @@ the value of an enumeration constant, the width of a bit-field, or
the initial value of a static variable.
If you don't know the type of the operand, you can still do this, but you
-must use @code{typeof} (@pxref{Typeof}) or type naming (@pxref{Naming
-Types}).
+must use @code{typeof} (@pxref{Typeof}).
Statement expressions are not supported fully in G++, and their fate
there is unclear. (It is possible that they will become fully supported
@@ -845,29 +843,6 @@ the containing function. You should specify, for @var{result}, a value
returned by @code{__builtin_apply}.
@end deftypefn
-@node Naming Types
-@section Naming an Expression's Type
-@cindex naming types
-
-You can give a name to the type of an expression using a @code{typedef}
-declaration with an initializer. Here is how to define @var{name} as a
-type name for the type of @var{exp}:
-
-@example
-typedef @var{name} = @var{exp};
-@end example
-
-This is useful in conjunction with the statements-within-expressions
-feature. Here is how the two together can be used to define a safe
-``maximum'' macro that operates on any arithmetic type:
-
-@example
-#define max(a,b) \
- (@{typedef _ta = (a), _tb = (b); \
- _ta _a = (a); _tb _b = (b); \
- _a > _b ? _a : _b; @})
-@end example
-
@cindex underscores in variables in macros
@cindex @samp{_} in variables in macros
@cindex local variables in macros
@@ -919,6 +894,21 @@ A @code{typeof}-construct can be used anywhere a typedef name could be
used. For example, you can use it in a declaration, in a cast, or inside
of @code{sizeof} or @code{typeof}.
+@code{typeof} is often useful in conjunction with the
+statements-within-expressions feature. Here is how the two together can
+be used to define a safe ``maximum'' macro that operates on any
+arithmetic type and evaluates each of its arguments exactly once:
+
+@example
+#define max(a,b) \
+ (@{ typeof (a) _a = (a); \
+ typeof (b) _b = (b); \
+ _a > _b ? _a : _b; @})
+@end example
+
+@noindent
+Some more examples of the use of @code{typeof}:
+
@itemize @bullet
@item
This declares @code{y} with the type of what @code{x} points to.
@@ -968,6 +958,26 @@ Thus, @code{array (pointer (char), 4)} is the type of arrays of 4
pointers to @code{char}.
@end itemize
+@emph{Compatibility Note:} In addition to @code{typeof}, GCC 2 supported
+a more limited extension which permitted one to write
+
+@example
+typedef @var{T} = @var{expr};
+@end example
+
+@noindent
+with the effect of declaring @var{T} to have the type of the expression
+@var{expr}. This extension does not work with GCC 3 (versions between
+3.0 and 3.2 will crash; 3.2.1 and later give an error). Code which
+relies on it should be rewritten to use @code{typeof}:
+
+@example
+typedef typeof(@var{expr}) @var{T};
+@end example
+
+@noindent
+This will work with all versions of GCC@.
+
@node Lvalues
@section Generalized Lvalues
@cindex compound expressions as lvalues
@@ -6170,12 +6180,12 @@ the minimum value of variables @var{i} and @var{j}.
However, side effects in @code{X} or @code{Y} may cause unintended
behavior. For example, @code{MIN (i++, j++)} will fail, incrementing
-the smaller counter twice. A GNU C extension allows you to write safe
-macros that avoid this kind of problem (@pxref{Naming Types,,Naming an
-Expression's Type}). However, writing @code{MIN} and @code{MAX} as
-macros also forces you to use function-call notation for a
-fundamental arithmetic operation. Using GNU C++ extensions, you can
-write @w{@samp{int min = i <? j;}} instead.
+the smaller counter twice. The GNU C @code{typeof} extension allows you
+to write safe macros that avoid this kind of problem (@pxref{Typeof}).
+However, writing @code{MIN} and @code{MAX} as macros also forces you to
+use function-call notation for a fundamental arithmetic operation.
+Using GNU C++ extensions, you can write @w{@samp{int min = i <? j;}}
+instead.
Since @code{<?} and @code{>?} are built into the compiler, they properly
handle expressions with side-effects; @w{@samp{int min = i++ <? j++;}}
diff --git a/contrib/gcc/doc/invoke.texi b/contrib/gcc/doc/invoke.texi
index d60d6fc..a56e3ed 100644
--- a/contrib/gcc/doc/invoke.texi
+++ b/contrib/gcc/doc/invoke.texi
@@ -222,7 +222,7 @@ in the following sections.
-Werror-implicit-function-declaration @gol
-Wimport -Winline @gol
-Wlarger-than-@var{len} -Wlong-long @gol
--Wmain -Wmissing-braces -Wmissing-declarations @gol
+-Wmain -Wmissing-braces @gol
-Wmissing-format-attribute -Wmissing-noreturn @gol
-Wmultichar -Wno-format-extra-args -Wno-format-y2k @gol
-Wno-import -Wpacked -Wpadded @gol
@@ -236,8 +236,8 @@ in the following sections.
@item C-only Warning Options
@gccoptlist{
--Wbad-function-cast -Wmissing-prototypes -Wnested-externs @gol
--Wstrict-prototypes -Wtraditional}
+-Wbad-function-cast -Wmissing-declarations -Wmissing-prototypes @gol
+-Wnested-externs -Wstrict-prototypes -Wtraditional}
@item Debugging Options
@xref{Debugging Options,,Options for Debugging Your Program or GCC}.
@@ -4246,15 +4246,13 @@ one @option{-I} option, the directories are scanned in left-to-right
order; the standard system directories come after.
If a standard system include directory, or a directory specified with
-@option{-isystem}, is also specified with @option{-I}, it will be
-searched only in the position requested by @option{-I}. Also, it will
-not be considered a system include directory. If that directory really
-does contain system headers, there is a good chance that they will
-break. For instance, if GCC's installation procedure edited the headers
-in @file{/usr/include} to fix bugs, @samp{-I/usr/include} will cause the
-original, buggy headers to be found instead of the corrected ones. GCC
-will issue a warning when a system include directory is hidden in this
-way.
+@option{-isystem}, is also specified with @option{-I}, the @option{-I}
+option will be ignored. The directory will still be searched but as a
+system directory at its normal position in the system include chain.
+This is to ensure that GCC's procedure to fix buggy system headers and
+the ordering for the include_next directive are not inadvertantly changed.
+If you really need to change the search order for system directories,
+use the @option{-nostdinc} and/or @option{-isystem} options.
@item -I-
@opindex I-
diff --git a/contrib/gcc/doloop.c b/contrib/gcc/doloop.c
index 6c0185c..06d8d57 100644
--- a/contrib/gcc/doloop.c
+++ b/contrib/gcc/doloop.c
@@ -552,6 +552,7 @@ doloop_modify_runtime (loop, iterations_max,
{
const struct loop_info *loop_info = LOOP_INFO (loop);
HOST_WIDE_INT abs_inc;
+ HOST_WIDE_INT abs_loop_inc;
int neg_inc;
rtx diff;
rtx sequence;
@@ -591,13 +592,22 @@ doloop_modify_runtime (loop, iterations_max,
n = abs (final - initial) / abs_inc;
n += (abs (final - initial) % abs_inc) != 0;
- If the loop has been unrolled, then the loop body has been
- preconditioned to iterate a multiple of unroll_number times. If
- abs_inc is != 1, the full calculation is
+ But when abs_inc is a power of two, the summation won't overflow
+ except in cases where the loop never terminates. So we don't
+ need to use this more costly calculation.
- t1 = abs_inc * unroll_number;
- n = abs (final - initial) / t1;
- n += (abs (final - initial) % t1) > t1 - abs_inc;
+ If the loop has been unrolled, the full calculation is
+
+ t1 = abs_inc * unroll_number; increment per loop
+ n = abs (final - initial) / t1; full loops
+ n += (abs (final - initial) % t1) != 0; partial loop
+
+ However, in certain cases the unrolled loop will be preconditioned
+ by emitting copies of the loop body with conditional branches,
+ so that the unrolled loop is always a full loop and thus needs
+ no exit tests. In this case we don't want to add the partial
+ loop count. As above, when t1 is a power of two we don't need to
+ worry about overflow.
The division and modulo operations can be avoided by requiring
that the increment is a power of 2 (precondition_loop_p enforces
@@ -658,58 +668,32 @@ doloop_modify_runtime (loop, iterations_max,
fprintf (loop_dump_stream,
"Doloop: Basic induction var skips initial incr.\n");
- diff = expand_simple_binop (mode, PLUS, diff, increment, diff,
- unsigned_p, OPTAB_LIB_WIDEN);
+ diff = expand_simple_binop (mode, PLUS, diff, GEN_INT (abs_inc),
+ diff, unsigned_p, OPTAB_LIB_WIDEN);
}
}
- if (abs_inc * loop_info->unroll_number != 1)
+ abs_loop_inc = abs_inc * loop_info->unroll_number;
+ if (abs_loop_inc != 1)
{
int shift_count;
- rtx extra;
- rtx label;
- unsigned HOST_WIDE_INT limit;
- shift_count = exact_log2 (abs_inc * loop_info->unroll_number);
+ shift_count = exact_log2 (abs_loop_inc);
if (shift_count < 0)
abort ();
- /* abs (final - initial) / (abs_inc * unroll_number) */
- iterations = expand_simple_binop (GET_MODE (diff), LSHIFTRT,
- diff, GEN_INT (shift_count),
- NULL_RTX, 1,
- OPTAB_LIB_WIDEN);
-
- if (abs_inc != 1)
- {
- /* abs (final - initial) % (abs_inc * unroll_number) */
- rtx count = GEN_INT (abs_inc * loop_info->unroll_number - 1);
- extra = expand_simple_binop (GET_MODE (iterations), AND,
- diff, count, NULL_RTX, 1,
- OPTAB_LIB_WIDEN);
-
- /* If (abs (final - initial) % (abs_inc * unroll_number)
- <= abs_inc * (unroll - 1)),
- jump past following increment instruction. */
- label = gen_label_rtx ();
- limit = abs_inc * (loop_info->unroll_number - 1);
- emit_cmp_and_jump_insns (extra, GEN_INT (limit),
- limit == 0 ? EQ : LEU, NULL_RTX,
- GET_MODE (extra), 0, label);
- JUMP_LABEL (get_last_insn ()) = label;
- LABEL_NUSES (label)++;
-
- /* Increment the iteration count by one. */
- iterations = expand_simple_binop (GET_MODE (iterations), PLUS,
- iterations, GEN_INT (1),
- iterations, 1,
- OPTAB_LIB_WIDEN);
+ if (!loop_info->preconditioned)
+ diff = expand_simple_binop (GET_MODE (diff), PLUS,
+ diff, GEN_INT (abs_loop_inc - 1),
+ diff, 1, OPTAB_LIB_WIDEN);
- emit_label (label);
- }
+ /* (abs (final - initial) + abs_inc * unroll_number - 1)
+ / (abs_inc * unroll_number) */
+ diff = expand_simple_binop (GET_MODE (diff), LSHIFTRT,
+ diff, GEN_INT (shift_count),
+ diff, 1, OPTAB_LIB_WIDEN);
}
- else
- iterations = diff;
+ iterations = diff;
/* If there is a NOTE_INSN_LOOP_VTOP, we have a `for' or `while'
style loop, with a loop exit test at the start. Thus, we can
@@ -722,17 +706,20 @@ doloop_modify_runtime (loop, iterations_max,
iteration count to one if necessary. */
if (! loop->vtop)
{
- rtx label;
-
if (loop_dump_stream)
fprintf (loop_dump_stream, "Doloop: Do-while loop.\n");
- /* A `do-while' loop must iterate at least once. If the
- iteration count is bogus, we set the iteration count to 1.
+ /* A `do-while' loop must iterate at least once. For code like
+ i = initial; do { ... } while (++i < final);
+ we will calculate a bogus iteration count if initial > final.
+ So detect this and set the iteration count to 1.
Note that if the loop has been unrolled, then the loop body
- is guaranteed to execute at least once. */
- if (loop_info->unroll_number == 1)
+ is guaranteed to execute at least once. Also, when the
+ comparison is NE, our calculated count will be OK. */
+ if (loop_info->unroll_number == 1 && comparison_code != NE)
{
+ rtx label;
+
/* Emit insns to test if the loop will immediately
terminate and to set the iteration count to 1 if true. */
label = gen_label_rtx();
diff --git a/contrib/gcc/expr.c b/contrib/gcc/expr.c
index 2a5c6f9..99f7fcf 100644
--- a/contrib/gcc/expr.c
+++ b/contrib/gcc/expr.c
@@ -5434,16 +5434,13 @@ rtx
force_operand (value, target)
rtx value, target;
{
- optab binoptab = 0;
- /* Use a temporary to force order of execution of calls to
- `force_operand'. */
- rtx tmp;
- rtx op2;
+ rtx op1, op2;
/* Use subtarget as the target for operand 0 of a binary operation. */
rtx subtarget = get_subtarget (target);
+ enum rtx_code code = GET_CODE (value);
/* Check for a PIC address load. */
- if ((GET_CODE (value) == PLUS || GET_CODE (value) == MINUS)
+ if ((code == PLUS || code == MINUS)
&& XEXP (value, 0) == pic_offset_table_rtx
&& (GET_CODE (XEXP (value, 1)) == SYMBOL_REF
|| GET_CODE (XEXP (value, 1)) == LABEL_REF
@@ -5455,60 +5452,88 @@ force_operand (value, target)
return subtarget;
}
- if (GET_CODE (value) == PLUS)
- binoptab = add_optab;
- else if (GET_CODE (value) == MINUS)
- binoptab = sub_optab;
- else if (GET_CODE (value) == MULT)
+ if (code == ZERO_EXTEND || code == SIGN_EXTEND)
{
- op2 = XEXP (value, 1);
- if (!CONSTANT_P (op2)
- && !(GET_CODE (op2) == REG && op2 != subtarget))
- subtarget = 0;
- tmp = force_operand (XEXP (value, 0), subtarget);
- return expand_mult (GET_MODE (value), tmp,
- force_operand (op2, NULL_RTX),
- target, 1);
+ if (!target)
+ target = gen_reg_rtx (GET_MODE (value));
+ convert_move (target, force_operand (XEXP (value, 0), NULL),
+ code == ZERO_EXTEND);
+ return target;
}
- if (binoptab)
+ if (GET_RTX_CLASS (code) == '2' || GET_RTX_CLASS (code) == 'c')
{
op2 = XEXP (value, 1);
- if (!CONSTANT_P (op2)
- && !(GET_CODE (op2) == REG && op2 != subtarget))
+ if (!CONSTANT_P (op2) && !(GET_CODE (op2) == REG && op2 != subtarget))
subtarget = 0;
- if (binoptab == sub_optab && GET_CODE (op2) == CONST_INT)
+ if (code == MINUS && GET_CODE (op2) == CONST_INT)
{
- binoptab = add_optab;
+ code = PLUS;
op2 = negate_rtx (GET_MODE (value), op2);
}
/* Check for an addition with OP2 a constant integer and our first
- operand a PLUS of a virtual register and something else. In that
- case, we want to emit the sum of the virtual register and the
- constant first and then add the other value. This allows virtual
- register instantiation to simply modify the constant rather than
- creating another one around this addition. */
- if (binoptab == add_optab && GET_CODE (op2) == CONST_INT
+ operand a PLUS of a virtual register and something else. In that
+ case, we want to emit the sum of the virtual register and the
+ constant first and then add the other value. This allows virtual
+ register instantiation to simply modify the constant rather than
+ creating another one around this addition. */
+ if (code == PLUS && GET_CODE (op2) == CONST_INT
&& GET_CODE (XEXP (value, 0)) == PLUS
&& GET_CODE (XEXP (XEXP (value, 0), 0)) == REG
&& REGNO (XEXP (XEXP (value, 0), 0)) >= FIRST_VIRTUAL_REGISTER
&& REGNO (XEXP (XEXP (value, 0), 0)) <= LAST_VIRTUAL_REGISTER)
{
- rtx temp = expand_binop (GET_MODE (value), binoptab,
- XEXP (XEXP (value, 0), 0), op2,
- subtarget, 0, OPTAB_LIB_WIDEN);
- return expand_binop (GET_MODE (value), binoptab, temp,
- force_operand (XEXP (XEXP (value, 0), 1), 0),
- target, 0, OPTAB_LIB_WIDEN);
+ rtx temp = expand_simple_binop (GET_MODE (value), code,
+ XEXP (XEXP (value, 0), 0), op2,
+ subtarget, 0, OPTAB_LIB_WIDEN);
+ return expand_simple_binop (GET_MODE (value), code, temp,
+ force_operand (XEXP (XEXP (value,
+ 0), 1), 0),
+ target, 0, OPTAB_LIB_WIDEN);
+ }
+
+ op1 = force_operand (XEXP (value, 0), subtarget);
+ op2 = force_operand (op2, NULL_RTX);
+ switch (code)
+ {
+ case MULT:
+ return expand_mult (GET_MODE (value), op1, op2, target, 1);
+ case DIV:
+ if (!INTEGRAL_MODE_P (GET_MODE (value)))
+ return expand_simple_binop (GET_MODE (value), code, op1, op2,
+ target, 1, OPTAB_LIB_WIDEN);
+ else
+ return expand_divmod (0,
+ FLOAT_MODE_P (GET_MODE (value))
+ ? RDIV_EXPR : TRUNC_DIV_EXPR,
+ GET_MODE (value), op1, op2, target, 0);
+ break;
+ case MOD:
+ return expand_divmod (1, TRUNC_MOD_EXPR, GET_MODE (value), op1, op2,
+ target, 0);
+ break;
+ case UDIV:
+ return expand_divmod (0, TRUNC_DIV_EXPR, GET_MODE (value), op1, op2,
+ target, 1);
+ break;
+ case UMOD:
+ return expand_divmod (1, TRUNC_MOD_EXPR, GET_MODE (value), op1, op2,
+ target, 1);
+ break;
+ case ASHIFTRT:
+ return expand_simple_binop (GET_MODE (value), code, op1, op2,
+ target, 0, OPTAB_LIB_WIDEN);
+ break;
+ default:
+ return expand_simple_binop (GET_MODE (value), code, op1, op2,
+ target, 1, OPTAB_LIB_WIDEN);
}
-
- tmp = force_operand (XEXP (value, 0), subtarget);
- return expand_binop (GET_MODE (value), binoptab, tmp,
- force_operand (op2, NULL_RTX),
- target, 0, OPTAB_LIB_WIDEN);
- /* We give UNSIGNEDP = 0 to expand_binop
- because the only operations we are expanding here are signed ones. */
+ }
+ if (GET_RTX_CLASS (code) == '1')
+ {
+ op1 = force_operand (XEXP (value, 0), NULL_RTX);
+ return expand_simple_unop (GET_MODE (value), code, op1, target, 0);
}
#ifdef INSN_SCHEDULING
@@ -7563,16 +7588,23 @@ expand_expr (exp, target, tmode, modifier)
}
}
+ if (! safe_from_p (subtarget, TREE_OPERAND (exp, 1), 1))
+ subtarget = 0;
+
/* No sense saving up arithmetic to be done
if it's all in the wrong mode to form part of an address.
And force_operand won't know whether to sign-extend or
zero-extend. */
if ((modifier != EXPAND_SUM && modifier != EXPAND_INITIALIZER)
|| mode != ptr_mode)
- goto binop;
-
- if (! safe_from_p (subtarget, TREE_OPERAND (exp, 1), 1))
- subtarget = 0;
+ {
+ op0 = expand_expr (TREE_OPERAND (exp, 0), subtarget, VOIDmode, 0);
+ op1 = expand_expr (TREE_OPERAND (exp, 1), NULL_RTX, VOIDmode, 0);
+ temp = simplify_binary_operation (PLUS, mode, op0, op1);
+ if (temp)
+ return temp;
+ goto binop2;
+ }
op0 = expand_expr (TREE_OPERAND (exp, 0), subtarget, VOIDmode, modifier);
op1 = expand_expr (TREE_OPERAND (exp, 1), NULL_RTX, VOIDmode, modifier);
diff --git a/contrib/gcc/f/version.c b/contrib/gcc/f/version.c
index b9dc05c..a420cc9 100644
--- a/contrib/gcc/f/version.c
+++ b/contrib/gcc/f/version.c
@@ -1,4 +1,4 @@
#include "ansidecl.h"
#include "f/version.h"
-const char *const ffe_version_string = "3.2.1 20020916 (prerelease)";
+const char *const ffe_version_string = "3.2.1 20021009 (prerelease)";
diff --git a/contrib/gcc/genmultilib b/contrib/gcc/genmultilib
index 3cbfaa1..ca3b71b 100644
--- a/contrib/gcc/genmultilib
+++ b/contrib/gcc/genmultilib
@@ -63,6 +63,14 @@
# for the rule to exclude a set. Options can be preceded with a '!' to
# match a logical NOT.
+# The optional sevenths argument is a list of OS subdirectory names.
+# The format is the same as of the second argument.
+# The difference is that second argument describes multilib directories
+# in GCC conventions, while this one the OS multilib convention.
+
+# The last option should be "yes" if multilibs are enabled. If it is not
+# "yes", all GCC multilib dir names will be ".".
+
# The output looks like
# #define MULTILIB_MATCHES "\
# SUBDIRECTORY OPTIONS;\
@@ -79,17 +87,18 @@
# Here is an example (this is from the actual sparc64 case):
# genmultilib 'm64/m32 mno-app-regs|mcmodel=medany' '64 32 alt'
# 'mcmodel?medany=mcmodel?medmid' 'm32/mno-app-regs* m32/mcmodel=*'
-# 'm32/!m64/mno-app-regs m32/!m64/mcmodel=medany'
+# '' 'm32/!m64/mno-app-regs m32/!m64/mcmodel=medany'
+# '../lib64 ../lib32 alt' yes
# This produces:
# ". !m64 !m32 !mno-app-regs !mcmodel=medany;",
-# "64 m64 !m32 !mno-app-regs !mcmodel=medany;",
-# "32 !m64 m32 !mno-app-regs !mcmodel=medany;",
+# "64:../lib64 m64 !m32 !mno-app-regs !mcmodel=medany;",
+# "32:../lib32 !m64 m32 !mno-app-regs !mcmodel=medany;",
# "alt !m64 !m32 mno-app-regs mcmodel=medany;",
# "alt !m64 !m32 mno-app-regs !mcmodel=medany;",
# "alt !m64 !m32 !mno-app-regs mcmodel=medany;",
-# "64/alt m64 !m32 mno-app-regs mcmodel=medany;",
-# "64/alt m64 !m32 mno-app-regs !mcmodel=medany;",
-# "64/alt m64 !m32 !mno-app-regs mcmodel=medany;",
+# "64/alt:../lib64/alt m64 !m32 mno-app-regs mcmodel=medany;",
+# "64/alt:../lib64/alt m64 !m32 mno-app-regs !mcmodel=medany;",
+# "64/alt:../lib64/alt m64 !m32 !mno-app-regs mcmodel=medany;",
#
# The effect is that `gcc -mno-app-regs' (for example) will append "alt"
# to the directory name when searching for libraries or startup files and
@@ -106,6 +115,8 @@ matches=$3
exceptions=$4
extra=$5
exclusions=$6
+osdirnames=$7
+enable_multilib=$8
echo "static const char *const multilib_raw[] = {"
@@ -202,6 +213,29 @@ if [ -n "${dirnames}" ]; then
done
fi
+# Construct a sed pattern which will convert option names to OS directory
+# names.
+toosdirnames=
+if [ -n "${osdirnames}" ]; then
+ set x ${osdirnames}
+ shift
+ for set in ${options}; do
+ for opts in `echo ${set} | sed -e 's|/| |'g`; do
+ patt="/"
+ for opt in `echo ${opts} | sed -e 's_|_ _'g`; do
+ if [ "$1" != "${opt}" ]; then
+ toosdirnames="${toosdirnames} -e s|/${opt}/|/${1}/|g"
+ patt="${patt}${1}/"
+ if [ "${patt}" != "/${1}/" ]; then
+ toosdirnames="${toosdirnames} -e s|${patt}|/${1}/|g"
+ fi
+ fi
+ done
+ shift
+ done
+ done
+fi
+
# We need another recursive shell script to correctly handle positive
# matches. If we are invoked as
# genmultilib "opt1 opt2" "" "opt1=nopt1 opt2=nopt2"
@@ -257,6 +291,25 @@ for combo in ${combinations}; do
# Remove the leading and trailing slashes.
dirout=`echo ${dirout} | sed -e 's|^/||' -e 's|/$||g'`
+ # Use the OS directory names rather than the option names.
+ if [ -n "${toosdirnames}" ]; then
+ osdirout=`echo ${combo} | sed ${toosdirnames}`
+ # Remove the leading and trailing slashes.
+ osdirout=`echo ${osdirout} | sed -e 's|^/||' -e 's|/$||g'`
+ if [ "x${enable_multilib}" != xyes ]; then
+ dirout=".:${osdirout}"
+ else
+ dirout="${dirout}:${osdirout}"
+ fi
+ else
+ if [ "x${enable_multilib}" != xyes ]; then
+ # genmultilib with --disable-multilib should be
+ # called with '' '' '' '' '' '' '' no
+ # if MULTILIB_OSDIRNAMES is empty.
+ exit 1
+ fi
+ fi
+
# Look through the options. We must output each option that is
# present, and negate each option that is not present.
optout=
@@ -313,6 +366,11 @@ done
echo "NULL"
echo "};"
+# Output the options now
+moptions=`echo ${options} | sed -e 's,[ ][ ]*, ,g'`
+echo ""
+echo "static const char *multilib_options = \"${moptions}\";"
+
rm -f tmpmultilib2
exit 0
diff --git a/contrib/gcc/jump.c b/contrib/gcc/jump.c
index cad10ff..1a26b59 100644
--- a/contrib/gcc/jump.c
+++ b/contrib/gcc/jump.c
@@ -2428,3 +2428,15 @@ true_regnum (x)
}
return -1;
}
+
+/* Return regno of the register REG and handle subregs too. */
+unsigned int
+reg_or_subregno (reg)
+ rtx reg;
+{
+ if (REG_P (reg))
+ return REGNO (reg);
+ if (GET_CODE (reg) == SUBREG)
+ return REGNO (SUBREG_REG (reg));
+ abort ();
+}
diff --git a/contrib/gcc/loop.c b/contrib/gcc/loop.c
index 4450845..732a84d 100644
--- a/contrib/gcc/loop.c
+++ b/contrib/gcc/loop.c
@@ -640,6 +640,7 @@ scan_loop (loop, flags)
int threshold;
/* Nonzero if we are scanning instructions in a sub-loop. */
int loop_depth = 0;
+ int in_libcall;
loop->top = 0;
@@ -756,290 +757,311 @@ scan_loop (loop, flags)
When MAYBE_NEVER is 0, all insns will be executed at least once
so that is not a problem. */
- for (p = next_insn_in_loop (loop, loop->scan_start);
+ for (in_libcall = 0, p = next_insn_in_loop (loop, loop->scan_start);
p != NULL_RTX;
p = next_insn_in_loop (loop, p))
{
- if (GET_CODE (p) == INSN
- && (set = single_set (p))
- && GET_CODE (SET_DEST (set)) == REG
-#ifdef PIC_OFFSET_TABLE_REG_CALL_CLOBBERED
- && SET_DEST (set) != pic_offset_table_rtx
-#endif
- && ! regs->array[REGNO (SET_DEST (set))].may_not_optimize)
+ if (in_libcall && INSN_P (p) && find_reg_note (p, REG_RETVAL, NULL_RTX))
+ in_libcall--;
+ if (GET_CODE (p) == INSN)
{
- int tem1 = 0;
- int tem2 = 0;
- int move_insn = 0;
- rtx src = SET_SRC (set);
- rtx dependencies = 0;
-
- /* Figure out what to use as a source of this insn. If a REG_EQUIV
- note is given or if a REG_EQUAL note with a constant operand is
- specified, use it as the source and mark that we should move
- this insn by calling emit_move_insn rather that duplicating the
- insn.
-
- Otherwise, only use the REG_EQUAL contents if a REG_RETVAL note
- is present. */
- temp = find_reg_note (p, REG_EQUIV, NULL_RTX);
+ temp = find_reg_note (p, REG_LIBCALL, NULL_RTX);
if (temp)
- src = XEXP (temp, 0), move_insn = 1;
- else
+ in_libcall++;
+ if (! in_libcall
+ && (set = single_set (p))
+ && GET_CODE (SET_DEST (set)) == REG
+#ifdef PIC_OFFSET_TABLE_REG_CALL_CLOBBERED
+ && SET_DEST (set) != pic_offset_table_rtx
+#endif
+ && ! regs->array[REGNO (SET_DEST (set))].may_not_optimize)
{
- temp = find_reg_note (p, REG_EQUAL, NULL_RTX);
- if (temp && CONSTANT_P (XEXP (temp, 0)))
+ int tem1 = 0;
+ int tem2 = 0;
+ int move_insn = 0;
+ rtx src = SET_SRC (set);
+ rtx dependencies = 0;
+
+ /* Figure out what to use as a source of this insn. If a
+ REG_EQUIV note is given or if a REG_EQUAL note with a
+ constant operand is specified, use it as the source and
+ mark that we should move this insn by calling
+ emit_move_insn rather that duplicating the insn.
+
+ Otherwise, only use the REG_EQUAL contents if a REG_RETVAL
+ note is present. */
+ temp = find_reg_note (p, REG_EQUIV, NULL_RTX);
+ if (temp)
src = XEXP (temp, 0), move_insn = 1;
- if (temp && find_reg_note (p, REG_RETVAL, NULL_RTX))
- {
- src = XEXP (temp, 0);
- /* A libcall block can use regs that don't appear in
- the equivalent expression. To move the libcall,
- we must move those regs too. */
- dependencies = libcall_other_reg (p, src);
- }
- }
-
- /* For parallels, add any possible uses to the depencies, as we can't move
- the insn without resolving them first. */
- if (GET_CODE (PATTERN (p)) == PARALLEL)
- {
- for (i = 0; i < XVECLEN (PATTERN (p), 0); i++)
+ else
{
- rtx x = XVECEXP (PATTERN (p), 0, i);
- if (GET_CODE (x) == USE)
- dependencies = gen_rtx_EXPR_LIST (VOIDmode, XEXP (x, 0), dependencies);
+ temp = find_reg_note (p, REG_EQUAL, NULL_RTX);
+ if (temp && CONSTANT_P (XEXP (temp, 0)))
+ src = XEXP (temp, 0), move_insn = 1;
+ if (temp && find_reg_note (p, REG_RETVAL, NULL_RTX))
+ {
+ src = XEXP (temp, 0);
+ /* A libcall block can use regs that don't appear in
+ the equivalent expression. To move the libcall,
+ we must move those regs too. */
+ dependencies = libcall_other_reg (p, src);
+ }
}
- }
- /* Don't try to optimize a register that was made
- by loop-optimization for an inner loop.
- We don't know its life-span, so we can't compute the benefit. */
- if (REGNO (SET_DEST (set)) >= max_reg_before_loop)
- ;
- else if (/* The register is used in basic blocks other
- than the one where it is set (meaning that
- something after this point in the loop might
- depend on its value before the set). */
- ! reg_in_basic_block_p (p, SET_DEST (set))
- /* And the set is not guaranteed to be executed once
- the loop starts, or the value before the set is
- needed before the set occurs...
-
- ??? Note we have quadratic behaviour here, mitigated
- by the fact that the previous test will often fail for
- large loops. Rather than re-scanning the entire loop
- each time for register usage, we should build tables
- of the register usage and use them here instead. */
- && (maybe_never
- || loop_reg_used_before_p (loop, set, p)))
- /* It is unsafe to move the set.
-
- This code used to consider it OK to move a set of a variable
- which was not created by the user and not used in an exit test.
- That behavior is incorrect and was removed. */
- ;
- else if ((tem = loop_invariant_p (loop, src))
- && (dependencies == 0
- || (tem2 = loop_invariant_p (loop, dependencies)) != 0)
- && (regs->array[REGNO (SET_DEST (set))].set_in_loop == 1
- || (tem1
- = consec_sets_invariant_p
- (loop, SET_DEST (set),
- regs->array[REGNO (SET_DEST (set))].set_in_loop,
- p)))
- /* If the insn can cause a trap (such as divide by zero),
- can't move it unless it's guaranteed to be executed
- once loop is entered. Even a function call might
- prevent the trap insn from being reached
- (since it might exit!) */
- && ! ((maybe_never || call_passed)
- && may_trap_p (src)))
- {
- struct movable *m;
- int regno = REGNO (SET_DEST (set));
-
- /* A potential lossage is where we have a case where two insns
- can be combined as long as they are both in the loop, but
- we move one of them outside the loop. For large loops,
- this can lose. The most common case of this is the address
- of a function being called.
-
- Therefore, if this register is marked as being used exactly
- once if we are in a loop with calls (a "large loop"), see if
- we can replace the usage of this register with the source
- of this SET. If we can, delete this insn.
-
- Don't do this if P has a REG_RETVAL note or if we have
- SMALL_REGISTER_CLASSES and SET_SRC is a hard register. */
-
- if (loop_info->has_call
- && regs->array[regno].single_usage != 0
- && regs->array[regno].single_usage != const0_rtx
- && REGNO_FIRST_UID (regno) == INSN_UID (p)
- && (REGNO_LAST_UID (regno)
- == INSN_UID (regs->array[regno].single_usage))
- && regs->array[regno].set_in_loop == 1
- && GET_CODE (SET_SRC (set)) != ASM_OPERANDS
- && ! side_effects_p (SET_SRC (set))
- && ! find_reg_note (p, REG_RETVAL, NULL_RTX)
- && (! SMALL_REGISTER_CLASSES
- || (! (GET_CODE (SET_SRC (set)) == REG
- && REGNO (SET_SRC (set)) < FIRST_PSEUDO_REGISTER)))
- /* This test is not redundant; SET_SRC (set) might be
- a call-clobbered register and the life of REGNO
- might span a call. */
- && ! modified_between_p (SET_SRC (set), p,
- regs->array[regno].single_usage)
- && no_labels_between_p (p, regs->array[regno].single_usage)
- && validate_replace_rtx (SET_DEST (set), SET_SRC (set),
- regs->array[regno].single_usage))
+ /* For parallels, add any possible uses to the depencies, as
+ we can't move the insn without resolving them first. */
+ if (GET_CODE (PATTERN (p)) == PARALLEL)
{
- /* Replace any usage in a REG_EQUAL note. Must copy the
- new source, so that we don't get rtx sharing between the
- SET_SOURCE and REG_NOTES of insn p. */
- REG_NOTES (regs->array[regno].single_usage)
- = replace_rtx (REG_NOTES (regs->array[regno].single_usage),
- SET_DEST (set), copy_rtx (SET_SRC (set)));
-
- delete_insn (p);
- for (i = 0; i < LOOP_REGNO_NREGS (regno, SET_DEST (set)); i++)
- regs->array[regno+i].set_in_loop = 0;
- continue;
+ for (i = 0; i < XVECLEN (PATTERN (p), 0); i++)
+ {
+ rtx x = XVECEXP (PATTERN (p), 0, i);
+ if (GET_CODE (x) == USE)
+ dependencies
+ = gen_rtx_EXPR_LIST (VOIDmode, XEXP (x, 0),
+ dependencies);
+ }
}
- m = (struct movable *) xmalloc (sizeof (struct movable));
- m->next = 0;
- m->insn = p;
- m->set_src = src;
- m->dependencies = dependencies;
- m->set_dest = SET_DEST (set);
- m->force = 0;
- m->consec = regs->array[REGNO (SET_DEST (set))].set_in_loop - 1;
- m->done = 0;
- m->forces = 0;
- m->partial = 0;
- m->move_insn = move_insn;
- m->move_insn_first = 0;
- m->is_equiv = (find_reg_note (p, REG_EQUIV, NULL_RTX) != 0);
- m->savemode = VOIDmode;
- m->regno = regno;
- /* Set M->cond if either loop_invariant_p
- or consec_sets_invariant_p returned 2
- (only conditionally invariant). */
- m->cond = ((tem | tem1 | tem2) > 1);
- m->global = LOOP_REG_GLOBAL_P (loop, regno);
- m->match = 0;
- m->lifetime = LOOP_REG_LIFETIME (loop, regno);
- m->savings = regs->array[regno].n_times_set;
- if (find_reg_note (p, REG_RETVAL, NULL_RTX))
- m->savings += libcall_benefit (p);
- for (i = 0; i < LOOP_REGNO_NREGS (regno, SET_DEST (set)); i++)
- regs->array[regno+i].set_in_loop = move_insn ? -2 : -1;
- /* Add M to the end of the chain MOVABLES. */
- loop_movables_add (movables, m);
-
- if (m->consec > 0)
+ /* Don't try to optimize a register that was made
+ by loop-optimization for an inner loop.
+ We don't know its life-span, so we can't compute
+ the benefit. */
+ if (REGNO (SET_DEST (set)) >= max_reg_before_loop)
+ ;
+ else if (/* The register is used in basic blocks other
+ than the one where it is set (meaning that
+ something after this point in the loop might
+ depend on its value before the set). */
+ ! reg_in_basic_block_p (p, SET_DEST (set))
+ /* And the set is not guaranteed to be executed once
+ the loop starts, or the value before the set is
+ needed before the set occurs...
+
+ ??? Note we have quadratic behaviour here, mitigated
+ by the fact that the previous test will often fail for
+ large loops. Rather than re-scanning the entire loop
+ each time for register usage, we should build tables
+ of the register usage and use them here instead. */
+ && (maybe_never
+ || loop_reg_used_before_p (loop, set, p)))
+ /* It is unsafe to move the set.
+
+ This code used to consider it OK to move a set of a variable
+ which was not created by the user and not used in an exit
+ test.
+ That behavior is incorrect and was removed. */
+ ;
+ else if ((tem = loop_invariant_p (loop, src))
+ && (dependencies == 0
+ || (tem2
+ = loop_invariant_p (loop, dependencies)) != 0)
+ && (regs->array[REGNO (SET_DEST (set))].set_in_loop == 1
+ || (tem1
+ = consec_sets_invariant_p
+ (loop, SET_DEST (set),
+ regs->array[REGNO (SET_DEST (set))].set_in_loop,
+ p)))
+ /* If the insn can cause a trap (such as divide by zero),
+ can't move it unless it's guaranteed to be executed
+ once loop is entered. Even a function call might
+ prevent the trap insn from being reached
+ (since it might exit!) */
+ && ! ((maybe_never || call_passed)
+ && may_trap_p (src)))
{
- /* It is possible for the first instruction to have a
- REG_EQUAL note but a non-invariant SET_SRC, so we must
- remember the status of the first instruction in case
- the last instruction doesn't have a REG_EQUAL note. */
- m->move_insn_first = m->move_insn;
-
- /* Skip this insn, not checking REG_LIBCALL notes. */
- p = next_nonnote_insn (p);
- /* Skip the consecutive insns, if there are any. */
- p = skip_consec_insns (p, m->consec);
- /* Back up to the last insn of the consecutive group. */
- p = prev_nonnote_insn (p);
-
- /* We must now reset m->move_insn, m->is_equiv, and possibly
- m->set_src to correspond to the effects of all the
- insns. */
- temp = find_reg_note (p, REG_EQUIV, NULL_RTX);
- if (temp)
- m->set_src = XEXP (temp, 0), m->move_insn = 1;
- else
+ struct movable *m;
+ int regno = REGNO (SET_DEST (set));
+
+ /* A potential lossage is where we have a case where two insns
+ can be combined as long as they are both in the loop, but
+ we move one of them outside the loop. For large loops,
+ this can lose. The most common case of this is the address
+ of a function being called.
+
+ Therefore, if this register is marked as being used
+ exactly once if we are in a loop with calls
+ (a "large loop"), see if we can replace the usage of
+ this register with the source of this SET. If we can,
+ delete this insn.
+
+ Don't do this if P has a REG_RETVAL note or if we have
+ SMALL_REGISTER_CLASSES and SET_SRC is a hard register. */
+
+ if (loop_info->has_call
+ && regs->array[regno].single_usage != 0
+ && regs->array[regno].single_usage != const0_rtx
+ && REGNO_FIRST_UID (regno) == INSN_UID (p)
+ && (REGNO_LAST_UID (regno)
+ == INSN_UID (regs->array[regno].single_usage))
+ && regs->array[regno].set_in_loop == 1
+ && GET_CODE (SET_SRC (set)) != ASM_OPERANDS
+ && ! side_effects_p (SET_SRC (set))
+ && ! find_reg_note (p, REG_RETVAL, NULL_RTX)
+ && (! SMALL_REGISTER_CLASSES
+ || (! (GET_CODE (SET_SRC (set)) == REG
+ && (REGNO (SET_SRC (set))
+ < FIRST_PSEUDO_REGISTER))))
+ /* This test is not redundant; SET_SRC (set) might be
+ a call-clobbered register and the life of REGNO
+ might span a call. */
+ && ! modified_between_p (SET_SRC (set), p,
+ regs->array[regno].single_usage)
+ && no_labels_between_p (p,
+ regs->array[regno].single_usage)
+ && validate_replace_rtx (SET_DEST (set), SET_SRC (set),
+ regs->array[regno].single_usage))
{
- temp = find_reg_note (p, REG_EQUAL, NULL_RTX);
- if (temp && CONSTANT_P (XEXP (temp, 0)))
- m->set_src = XEXP (temp, 0), m->move_insn = 1;
- else
- m->move_insn = 0;
+ /* Replace any usage in a REG_EQUAL note. Must copy
+ the new source, so that we don't get rtx sharing
+ between the SET_SOURCE and REG_NOTES of insn p. */
+ REG_NOTES (regs->array[regno].single_usage)
+ = (replace_rtx
+ (REG_NOTES (regs->array[regno].single_usage),
+ SET_DEST (set), copy_rtx (SET_SRC (set))));
+ delete_insn (p);
+ for (i = 0; i < LOOP_REGNO_NREGS (regno, SET_DEST (set));
+ i++)
+ regs->array[regno+i].set_in_loop = 0;
+ continue;
}
- m->is_equiv = (find_reg_note (p, REG_EQUIV, NULL_RTX) != 0);
- }
- }
- /* If this register is always set within a STRICT_LOW_PART
- or set to zero, then its high bytes are constant.
- So clear them outside the loop and within the loop
- just load the low bytes.
- We must check that the machine has an instruction to do so.
- Also, if the value loaded into the register
- depends on the same register, this cannot be done. */
- else if (SET_SRC (set) == const0_rtx
- && GET_CODE (NEXT_INSN (p)) == INSN
- && (set1 = single_set (NEXT_INSN (p)))
- && GET_CODE (set1) == SET
- && (GET_CODE (SET_DEST (set1)) == STRICT_LOW_PART)
- && (GET_CODE (XEXP (SET_DEST (set1), 0)) == SUBREG)
- && (SUBREG_REG (XEXP (SET_DEST (set1), 0))
- == SET_DEST (set))
- && !reg_mentioned_p (SET_DEST (set), SET_SRC (set1)))
- {
- int regno = REGNO (SET_DEST (set));
- if (regs->array[regno].set_in_loop == 2)
- {
- struct movable *m;
+
m = (struct movable *) xmalloc (sizeof (struct movable));
m->next = 0;
m->insn = p;
+ m->set_src = src;
+ m->dependencies = dependencies;
m->set_dest = SET_DEST (set);
- m->dependencies = 0;
m->force = 0;
- m->consec = 0;
+ m->consec
+ = regs->array[REGNO (SET_DEST (set))].set_in_loop - 1;
m->done = 0;
m->forces = 0;
- m->move_insn = 0;
+ m->partial = 0;
+ m->move_insn = move_insn;
m->move_insn_first = 0;
- m->partial = 1;
- /* If the insn may not be executed on some cycles,
- we can't clear the whole reg; clear just high part.
- Not even if the reg is used only within this loop.
- Consider this:
- while (1)
- while (s != t) {
- if (foo ()) x = *s;
- use (x);
- }
- Clearing x before the inner loop could clobber a value
- being saved from the last time around the outer loop.
- However, if the reg is not used outside this loop
- and all uses of the register are in the same
- basic block as the store, there is no problem.
-
- If this insn was made by loop, we don't know its
- INSN_LUID and hence must make a conservative
- assumption. */
- m->global = (INSN_UID (p) >= max_uid_for_loop
- || LOOP_REG_GLOBAL_P (loop, regno)
- || (labels_in_range_p
- (p, REGNO_FIRST_LUID (regno))));
- if (maybe_never && m->global)
- m->savemode = GET_MODE (SET_SRC (set1));
- else
- m->savemode = VOIDmode;
+ m->is_equiv = (find_reg_note (p, REG_EQUIV, NULL_RTX) != 0);
+ m->savemode = VOIDmode;
m->regno = regno;
- m->cond = 0;
+ /* Set M->cond if either loop_invariant_p
+ or consec_sets_invariant_p returned 2
+ (only conditionally invariant). */
+ m->cond = ((tem | tem1 | tem2) > 1);
+ m->global = LOOP_REG_GLOBAL_P (loop, regno);
m->match = 0;
m->lifetime = LOOP_REG_LIFETIME (loop, regno);
- m->savings = 1;
+ m->savings = regs->array[regno].n_times_set;
+ if (find_reg_note (p, REG_RETVAL, NULL_RTX))
+ m->savings += libcall_benefit (p);
for (i = 0; i < LOOP_REGNO_NREGS (regno, SET_DEST (set)); i++)
- regs->array[regno+i].set_in_loop = -1;
+ regs->array[regno+i].set_in_loop = move_insn ? -2 : -1;
/* Add M to the end of the chain MOVABLES. */
loop_movables_add (movables, m);
+
+ if (m->consec > 0)
+ {
+ /* It is possible for the first instruction to have a
+ REG_EQUAL note but a non-invariant SET_SRC, so we must
+ remember the status of the first instruction in case
+ the last instruction doesn't have a REG_EQUAL note. */
+ m->move_insn_first = m->move_insn;
+
+ /* Skip this insn, not checking REG_LIBCALL notes. */
+ p = next_nonnote_insn (p);
+ /* Skip the consecutive insns, if there are any. */
+ p = skip_consec_insns (p, m->consec);
+ /* Back up to the last insn of the consecutive group. */
+ p = prev_nonnote_insn (p);
+
+ /* We must now reset m->move_insn, m->is_equiv, and
+ possibly m->set_src to correspond to the effects of
+ all the insns. */
+ temp = find_reg_note (p, REG_EQUIV, NULL_RTX);
+ if (temp)
+ m->set_src = XEXP (temp, 0), m->move_insn = 1;
+ else
+ {
+ temp = find_reg_note (p, REG_EQUAL, NULL_RTX);
+ if (temp && CONSTANT_P (XEXP (temp, 0)))
+ m->set_src = XEXP (temp, 0), m->move_insn = 1;
+ else
+ m->move_insn = 0;
+
+ }
+ m->is_equiv
+ = (find_reg_note (p, REG_EQUIV, NULL_RTX) != 0);
+ }
+ }
+ /* If this register is always set within a STRICT_LOW_PART
+ or set to zero, then its high bytes are constant.
+ So clear them outside the loop and within the loop
+ just load the low bytes.
+ We must check that the machine has an instruction to do so.
+ Also, if the value loaded into the register
+ depends on the same register, this cannot be done. */
+ else if (SET_SRC (set) == const0_rtx
+ && GET_CODE (NEXT_INSN (p)) == INSN
+ && (set1 = single_set (NEXT_INSN (p)))
+ && GET_CODE (set1) == SET
+ && (GET_CODE (SET_DEST (set1)) == STRICT_LOW_PART)
+ && (GET_CODE (XEXP (SET_DEST (set1), 0)) == SUBREG)
+ && (SUBREG_REG (XEXP (SET_DEST (set1), 0))
+ == SET_DEST (set))
+ && !reg_mentioned_p (SET_DEST (set), SET_SRC (set1)))
+ {
+ int regno = REGNO (SET_DEST (set));
+ if (regs->array[regno].set_in_loop == 2)
+ {
+ struct movable *m;
+ m = (struct movable *) xmalloc (sizeof (struct movable));
+ m->next = 0;
+ m->insn = p;
+ m->set_dest = SET_DEST (set);
+ m->dependencies = 0;
+ m->force = 0;
+ m->consec = 0;
+ m->done = 0;
+ m->forces = 0;
+ m->move_insn = 0;
+ m->move_insn_first = 0;
+ m->partial = 1;
+ /* If the insn may not be executed on some cycles,
+ we can't clear the whole reg; clear just high part.
+ Not even if the reg is used only within this loop.
+ Consider this:
+ while (1)
+ while (s != t) {
+ if (foo ()) x = *s;
+ use (x);
+ }
+ Clearing x before the inner loop could clobber a value
+ being saved from the last time around the outer loop.
+ However, if the reg is not used outside this loop
+ and all uses of the register are in the same
+ basic block as the store, there is no problem.
+
+ If this insn was made by loop, we don't know its
+ INSN_LUID and hence must make a conservative
+ assumption. */
+ m->global = (INSN_UID (p) >= max_uid_for_loop
+ || LOOP_REG_GLOBAL_P (loop, regno)
+ || (labels_in_range_p
+ (p, REGNO_FIRST_LUID (regno))));
+ if (maybe_never && m->global)
+ m->savemode = GET_MODE (SET_SRC (set1));
+ else
+ m->savemode = VOIDmode;
+ m->regno = regno;
+ m->cond = 0;
+ m->match = 0;
+ m->lifetime = LOOP_REG_LIFETIME (loop, regno);
+ m->savings = 1;
+ for (i = 0; i < LOOP_REGNO_NREGS (regno, SET_DEST (set));
+ i++)
+ regs->array[regno+i].set_in_loop = -1;
+ /* Add M to the end of the chain MOVABLES. */
+ loop_movables_add (movables, m);
+ }
}
}
}
@@ -1911,10 +1933,10 @@ move_movables (loop, movables, threshold, insn_count)
for (count = m->consec; count >= 0; count--)
{
/* If this is the first insn of a library call sequence,
- skip to the end. */
+ something is very wrong. */
if (GET_CODE (p) != NOTE
&& (temp = find_reg_note (p, REG_LIBCALL, NULL_RTX)))
- p = XEXP (temp, 0);
+ abort ();
/* If this is the last insn of a libcall sequence, then
delete every insn in the sequence except the last.
@@ -4090,11 +4112,17 @@ emit_prefetch_instructions (loop)
{
rtx reg = gen_reg_rtx (Pmode);
rtx loop_start = loop->start;
+ rtx init_val = info[i].class->initial_value;
rtx add_val = simplify_gen_binary (PLUS, Pmode,
info[i].giv->add_val,
GEN_INT (y * PREFETCH_BLOCK));
- loop_iv_add_mult_emit_before (loop, info[i].class->initial_value,
+ /* Functions called by LOOP_IV_ADD_EMIT_BEFORE expect a
+ non-constant INIT_VAL to have the same mode as REG, which
+ in this case we know to be Pmode. */
+ if (GET_MODE (init_val) != Pmode && !CONSTANT_P (init_val))
+ init_val = convert_to_mode (Pmode, init_val, 0);
+ loop_iv_add_mult_emit_before (loop, init_val,
info[i].giv->mult_val,
add_val, reg, 0, loop_start);
emit_insn_before (gen_prefetch (reg, GEN_INT (info[i].write),
diff --git a/contrib/gcc/loop.h b/contrib/gcc/loop.h
index 8e3a935..6d18b01 100644
--- a/contrib/gcc/loop.h
+++ b/contrib/gcc/loop.h
@@ -314,6 +314,9 @@ struct loop_info
int has_multiple_exit_targets;
/* Nonzero if there is an indirect jump in the current function. */
int has_indirect_jump;
+ /* Whether loop unrolling has emitted copies of the loop body so
+ that the main loop needs no exit tests. */
+ int preconditioned;
/* Register or constant initial loop value. */
rtx initial_value;
/* Register or constant value used for comparison test. */
diff --git a/contrib/gcc/mklibgcc.in b/contrib/gcc/mklibgcc.in
index c5db6f0..30f660c 100644
--- a/contrib/gcc/mklibgcc.in
+++ b/contrib/gcc/mklibgcc.in
@@ -32,7 +32,7 @@
# SHLIB_MAPFILES
# SHLIB_NM_FLAGS
# SHLIB_INSTALL
-# SHLIB_SLIBDIR_SUFFIXES
+# MULTILIB_OSDIRNAMES
# Make needs VPATH to be literal.
echo 'srcdir = @srcdir@'
@@ -317,22 +317,18 @@ for ml in $MULTILIBS; do
fi
shlib_so_name="$shlib_base_name"
shlib_dir=
- if [ -n "$SHLIB_SLIBDIR_SUFFIXES" ]; then
+ if [ -n "$MULTILIB_OSDIRNAMES" ]; then
if [ "$dir" != . ]; then
+ gcc_multilib_dir=`./xgcc -B./ $flags --print-multi-directory`
+ os_multilib_dir=`./xgcc -B./ $flags --print-multi-os-directory`
shlib_dir="$dir"/
- for suffix_pair in $SHLIB_SLIBDIR_SUFFIXES ; do
- base_ml_dir=`echo ${suffix_pair} | sed -e 's/:.*$//' -e 's/=/$(EQ)/g'`
- if [ "$dir" = "$base_ml_dir" ]; then
- shlib_so_name=libgcc_s
- break
- else
- canon_dir=`echo $dir | sed -n -e "s:$base_ml_dir/::p"`
- if [ -n "$canon_dir" ]; then
- shlib_so_name=libgcc_s_`echo $canon_dir | sed s,/,_,g`
- break
- fi
- fi
- done
+ gcc_multilib_sup=`echo $gcc_multilib_dir | sed 's~^[^/]*/~~'`
+ os_multilib_base=`echo $os_multilib_dir | sed -n "s~/${gcc_multilib_sup}\$~~p"`
+ if [ -z "$os_multilib_base" ]; then
+ shlib_so_name=libgcc_s
+ else
+ shlib_so_name=libgcc_s_`echo $gcc_multilib_sup | sed s,/,_,g`
+ fi
fi
fi
echo ""
@@ -438,6 +434,7 @@ echo ""
echo "install: $all"
for ml in $MULTILIBS; do
dir=`echo ${ml} | sed -e 's/;.*$//' -e 's/=/$(EQ)/g'`
+ flags=`echo ${ml} | sed -e 's/^[^;]*;//' -e 's/@/ -/g'`;
if [ $dir != . ]; then
ldir='$(libsubdir)'/$dir
echo " if [ -d $ldir ]; then true; else mkdir $ldir; chmod a+rx $ldir; fi;"
@@ -460,39 +457,22 @@ for ml in $MULTILIBS; do
shlib_so_name="$shlib_base_name"
shlib_dir=
shlib_slibdir_qual=
- if [ -n "$SHLIB_SLIBDIR_SUFFIXES" ]; then
- shlib_slibdir_qual=none
+ if [ -n "$MULTILIB_OSDIRNAMES" ]; then
+ gcc_multilib_dir=`./xgcc -B./ $flags --print-multi-directory`
+ os_multilib_dir=`./xgcc -B./ $flags --print-multi-os-directory`
if [ "$dir" != . ]; then
shlib_dir="$dir"/
- for suffix_pair in $SHLIB_SLIBDIR_SUFFIXES ; do
- base_ml_dir=`echo ${suffix_pair} | sed -e 's/:.*$//' -e 's/=/$(EQ)/g'`
- if [ "$dir" = "$base_ml_dir" ]; then
- shlib_so_name=libgcc_s
- shlib_slibdir_qual=`echo ${suffix_pair} | sed -e 's/^[^:]*://'`
- break
- else
- canon_dir=`echo $dir | sed -n -e "s:$base_ml_dir/::p"`
- if [ -n "$canon_dir" ]; then
- shlib_so_name=libgcc_s_`echo $canon_dir | sed s,/,_,g`
- shlib_slibdir_qual=`echo ${suffix_pair} | sed -e 's/^[^:]*://'`
- break
- fi
- fi
- done
fi
- if [ "$shlib_slibdir_qual" = none ]; then
- for suffix_pair in $SHLIB_SLIBDIR_SUFFIXES ; do
- base_ml_dir=`echo ${suffix_pair} | sed -e 's/:.*$//' -e 's/=/$(EQ)/g'`
- shlib_slibdir_qual=`echo ${suffix_pair} | sed -e 's/^[^:]*://'`
- for ml2 in $MULTILIBS; do
- dir2=`echo ${ml2} | sed -e 's/;.*$//' -e 's/=/$(EQ)/g'`
- if [ "$base_ml_dir" = "$dir2" ]; then
- shlib_slibdir_qual=
- break
- fi
- done
- if [ -n "$shlib_slibdir_qual" ]; then break; fi
- done
+ gcc_multilib_sup=`echo $gcc_multilib_dir | sed 's~^[^/]*/~~'`
+ os_multilib_base=`echo $os_multilib_dir | sed -n "s~/${gcc_multilib_sup}\$~~p"`
+ if [ -z "$os_multilib_base" ]; then
+ shlib_so_name=libgcc_s
+ if [ "$os_multilib_dir" != "." ]; then
+ shlib_slibdir_qual="/$os_multilib_dir"
+ fi
+ else
+ shlib_so_name=libgcc_s_`echo $gcc_multilib_sup | sed s,/,_,g`
+ shlib_slibdir_qual="/$os_multilib_base"
fi
fi
echo " $SHLIB_INSTALL" \
diff --git a/contrib/gcc/reload1.c b/contrib/gcc/reload1.c
index 0ce10c4..9782f3a 100644
--- a/contrib/gcc/reload1.c
+++ b/contrib/gcc/reload1.c
@@ -7354,6 +7354,9 @@ gen_reload (out, in, opnum, type)
{
rtx last = get_last_insn ();
rtx tem;
+#ifdef SECONDARY_MEMORY_NEEDED
+ int in_regnum, out_regnum;
+#endif
/* If IN is a paradoxical SUBREG, remove it and try to put the
opposite SUBREG on OUT. Likewise for a paradoxical SUBREG on OUT. */
@@ -7516,20 +7519,22 @@ gen_reload (out, in, opnum, type)
#ifdef SECONDARY_MEMORY_NEEDED
/* If we need a memory location to do the move, do it that way. */
- else if (GET_CODE (in) == REG && REGNO (in) < FIRST_PSEUDO_REGISTER
- && GET_CODE (out) == REG && REGNO (out) < FIRST_PSEUDO_REGISTER
- && SECONDARY_MEMORY_NEEDED (REGNO_REG_CLASS (REGNO (in)),
- REGNO_REG_CLASS (REGNO (out)),
+ else if ((in_regnum = true_regnum (in)) >= 0
+ && in_regnum < FIRST_PSEUDO_REGISTER
+ && (out_regnum = true_regnum (out)) >= 0
+ && out_regnum < FIRST_PSEUDO_REGISTER
+ && SECONDARY_MEMORY_NEEDED (REGNO_REG_CLASS (in_regnum),
+ REGNO_REG_CLASS (out_regnum),
GET_MODE (out)))
{
/* Get the memory to use and rewrite both registers to its mode. */
rtx loc = get_secondary_mem (in, GET_MODE (out), opnum, type);
if (GET_MODE (loc) != GET_MODE (out))
- out = gen_rtx_REG (GET_MODE (loc), REGNO (out));
+ out = gen_rtx_REG (GET_MODE (loc), out_regnum);
if (GET_MODE (loc) != GET_MODE (in))
- in = gen_rtx_REG (GET_MODE (loc), REGNO (in));
+ in = gen_rtx_REG (GET_MODE (loc), in_regnum);
gen_reload (loc, in, opnum, type);
gen_reload (out, loc, opnum, type);
@@ -7581,6 +7586,11 @@ delete_output_reload (insn, j, last_reload_reg)
rtx i1;
rtx substed;
+ /* It is possible that this reload has been only used to set another reload
+ we eliminated earlier and thus deleted this instruction too. */
+ if (INSN_DELETED_P (output_reload_insn))
+ return;
+
/* Get the raw pseudo-register referred to. */
while (GET_CODE (reg) == SUBREG)
diff --git a/contrib/gcc/rtl.h b/contrib/gcc/rtl.h
index 12f994b..63b9f58 100644
--- a/contrib/gcc/rtl.h
+++ b/contrib/gcc/rtl.h
@@ -1811,6 +1811,7 @@ extern int invert_jump_1 PARAMS ((rtx, rtx));
extern int invert_jump PARAMS ((rtx, rtx, int));
extern int rtx_renumbered_equal_p PARAMS ((rtx, rtx));
extern int true_regnum PARAMS ((rtx));
+extern unsigned int reg_or_subregno PARAMS ((rtx));
extern int redirect_jump_1 PARAMS ((rtx, rtx));
extern int redirect_jump PARAMS ((rtx, rtx, int));
extern void rebuild_jump_labels PARAMS ((rtx));
diff --git a/contrib/gcc/sched-deps.c b/contrib/gcc/sched-deps.c
index f2f64d3..4e14ee2 100644
--- a/contrib/gcc/sched-deps.c
+++ b/contrib/gcc/sched-deps.c
@@ -923,7 +923,15 @@ sched_analyze_insn (deps, x, insn, loop_notes)
code = GET_CODE (x);
}
if (code == SET || code == CLOBBER)
- sched_analyze_1 (deps, x, insn);
+ {
+ sched_analyze_1 (deps, x, insn);
+
+ /* Bare clobber insns are used for letting life analysis, reg-stack
+ and others know that a value is dead. Depend on the last call
+ instruction so that reg-stack won't get confused. */
+ if (code == CLOBBER)
+ add_dependence_list (insn, deps->last_function_call, REG_DEP_OUTPUT);
+ }
else if (code == PARALLEL)
{
int i;
diff --git a/contrib/gcc/sibcall.c b/contrib/gcc/sibcall.c
index 6e753fa..fca451f 100644
--- a/contrib/gcc/sibcall.c
+++ b/contrib/gcc/sibcall.c
@@ -574,8 +574,8 @@ optimize_sibling_and_tail_recursive_calls ()
rtx insn, insns;
basic_block alternate_exit = EXIT_BLOCK_PTR;
bool no_sibcalls_this_function = false;
- int successful_sibling_call = 0;
- int replaced_call_placeholder = 0;
+ bool successful_replacement = false;
+ bool replaced_call_placeholder = false;
edge e;
insns = get_insns ();
@@ -715,10 +715,11 @@ optimize_sibling_and_tail_recursive_calls ()
/* Select a set of insns to implement the call and emit them.
Tail recursion is the most efficient, so select it over
a tail/sibling call. */
- if (sibcall)
- successful_sibling_call = 1;
- replaced_call_placeholder = 1;
+ if (sibcall || tailrecursion)
+ successful_replacement = true;
+ replaced_call_placeholder = true;
+
replace_call_placeholder (insn,
tailrecursion != 0
? sibcall_use_tail_recursion
@@ -728,7 +729,7 @@ optimize_sibling_and_tail_recursive_calls ()
}
}
- if (successful_sibling_call)
+ if (successful_replacement)
{
rtx insn;
tree arg;
diff --git a/contrib/gcc/tree.h b/contrib/gcc/tree.h
index 9346f7d..084c306 100644
--- a/contrib/gcc/tree.h
+++ b/contrib/gcc/tree.h
@@ -2052,6 +2052,33 @@ extern tree integer_types[itk_none];
#define long_long_unsigned_type_node integer_types[itk_unsigned_long_long]
+/* A pointer-to-function member type looks like:
+
+ struct {
+ __P __pfn;
+ ptrdiff_t __delta;
+ };
+
+ If __pfn is NULL, it is a NULL pointer-to-member-function.
+
+ (Because the vtable is always the first thing in the object, we
+ don't need its offset.) If the function is virtual, then PFN is
+ one plus twice the index into the vtable; otherwise, it is just a
+ pointer to the function.
+
+ Unfortunately, using the lowest bit of PFN doesn't work in
+ architectures that don't impose alignment requirements on function
+ addresses, or that use the lowest bit to tell one ISA from another,
+ for example. For such architectures, we use the lowest bit of
+ DELTA instead of the lowest bit of the PFN, and DELTA will be
+ multiplied by 2. */
+
+enum ptrmemfunc_vbit_where_t
+{
+ ptrmemfunc_vbit_in_pfn,
+ ptrmemfunc_vbit_in_delta
+};
+
#define NULL_TREE (tree) NULL
/* Approximate positive square root of a host double. This is for
diff --git a/contrib/gcc/unroll.c b/contrib/gcc/unroll.c
index 032d675..83327c7 100644
--- a/contrib/gcc/unroll.c
+++ b/contrib/gcc/unroll.c
@@ -1188,6 +1188,9 @@ unroll_loop (loop, insn_count, strength_reduce_p)
/* Keep track of the unroll factor for the loop. */
loop_info->unroll_number = unroll_number;
+ /* And whether the loop has been preconditioned. */
+ loop_info->preconditioned = loop_preconditioned;
+
/* For each biv and giv, determine whether it can be safely split into
a different variable for each unrolled copy of the loop body.
We precalculate and save this info here, since computing it is
@@ -2868,7 +2871,7 @@ find_splittable_givs (loop, bl, unroll_type, increment, unroll_number)
value = tem;
}
- splittable_regs[REGNO (v->new_reg)] = value;
+ splittable_regs[reg_or_subregno (v->new_reg)] = value;
}
else
{
@@ -3047,21 +3050,21 @@ find_splittable_givs (loop, bl, unroll_type, increment, unroll_number)
itself does not have to be splittable. */
if (v->same && v->same->giv_type == DEST_REG)
- addr_combined_regs[REGNO (v->same->new_reg)] = v->same;
+ addr_combined_regs[reg_or_subregno (v->same->new_reg)] = v->same;
if (GET_CODE (v->new_reg) == REG)
{
/* This giv maybe hasn't been combined with any others.
Make sure that it's giv is marked as splittable here. */
- splittable_regs[REGNO (v->new_reg)] = value;
+ splittable_regs[reg_or_subregno (v->new_reg)] = value;
/* Make it appear to depend upon itself, so that the
giv will be properly split in the main loop above. */
if (! v->same)
{
v->same = v;
- addr_combined_regs[REGNO (v->new_reg)] = v;
+ addr_combined_regs[reg_or_subregno (v->new_reg)] = v;
}
}
@@ -3098,7 +3101,7 @@ find_splittable_givs (loop, bl, unroll_type, increment, unroll_number)
if (! v->ignore)
count = REG_IV_CLASS (ivs, REGNO (v->src_reg))->biv_count;
- splittable_regs_updates[REGNO (v->new_reg)] = count;
+ splittable_regs_updates[reg_or_subregno (v->new_reg)] = count;
}
result++;
diff --git a/contrib/gcc/varasm.c b/contrib/gcc/varasm.c
index 4c27011..9e683a5 100644
--- a/contrib/gcc/varasm.c
+++ b/contrib/gcc/varasm.c
@@ -1194,6 +1194,8 @@ assemble_start_function (decl, fnname)
/* Tell assembler to move to target machine's alignment for functions. */
align = floor_log2 (FUNCTION_BOUNDARY / BITS_PER_UNIT);
+ if (align < force_align_functions_log)
+ align = force_align_functions_log;
if (align > 0)
{
ASM_OUTPUT_ALIGN (asm_out_file, align);
OpenPOWER on IntegriCloud