Gcc 3.4.4 release.
This commit is contained in:
parent
1689e31de6
commit
d51085f37e
File diff suppressed because it is too large
Load Diff
@ -505,8 +505,16 @@ CRTSTUFF_CFLAGS = -O2 $(GCC_CFLAGS) $(INCLUDES) $(MULTILIB_CFLAGS) -g0 \
|
||||
# Additional sources to handle exceptions; overridden by targets as needed.
|
||||
LIB2ADDEH = $(srcdir)/unwind-dw2.c $(srcdir)/unwind-dw2-fde.c \
|
||||
$(srcdir)/unwind-sjlj.c $(srcdir)/gthr-gnat.c $(srcdir)/unwind-c.c
|
||||
LIB2ADDEHSTATIC = $(LIB2ADDEH)
|
||||
LIB2ADDEHSHARED = $(LIB2ADDEH)
|
||||
LIB2ADDEHDEP = unwind.inc unwind-dw2-fde.h
|
||||
|
||||
# Don't build libunwind by default.
|
||||
LIBUNWIND =
|
||||
LIBUNWINDDEP =
|
||||
SHLIBUNWIND_LINK =
|
||||
SHLIBUNWIND_INSTALL =
|
||||
|
||||
# nm flags to list global symbols in libgcc object files.
|
||||
SHLIB_NM_FLAGS = -pg
|
||||
|
||||
@ -545,6 +553,10 @@ LIB2FUNCS_EXTRA =
|
||||
# Assembler files should have names ending in `.asm'.
|
||||
LIB2FUNCS_STATIC_EXTRA =
|
||||
|
||||
# List of extra C and assembler files to add to shared libgcc2.
|
||||
# Assembler files should have names ending in `.asm'.
|
||||
LIB2FUNCS_SHARED_EXTRA =
|
||||
|
||||
# Program to convert libraries.
|
||||
LIBCONVERT =
|
||||
|
||||
@ -938,6 +950,9 @@ LIB2_DIVMOD_FUNCS = _divdi3 _moddi3 _udivdi3 _umoddi3 _udiv_w_sdiv _udivmoddi4
|
||||
# language hooks, generated by configure
|
||||
@language_hooks@
|
||||
|
||||
# Set up library path if needed.
|
||||
@set_gcc_lib_path@
|
||||
|
||||
# per-language makefile fragments
|
||||
ifneq ($(LANG_MAKEFRAGS),)
|
||||
include $(LANG_MAKEFRAGS)
|
||||
@ -1133,16 +1148,25 @@ xlimits.h: glimits.h limitx.h limity.h
|
||||
|
||||
LIB2ADD = $(LIB2FUNCS_EXTRA)
|
||||
LIB2ADD_ST = $(LIB2FUNCS_STATIC_EXTRA)
|
||||
LIB2ADD_SH = $(LIB2FUNCS_SHARED_EXTRA)
|
||||
|
||||
libgcc.mk: config.status Makefile mklibgcc $(LIB2ADD) $(LIB2ADD_ST) xgcc$(exeext) specs
|
||||
libgcc.mk: config.status Makefile mklibgcc $(LIB2ADD) $(LIB2ADD_ST) $(LIB2ADD_SH) \
|
||||
xgcc$(exeext) specs
|
||||
objext='$(objext)' \
|
||||
LIB1ASMFUNCS='$(LIB1ASMFUNCS)' \
|
||||
LIB2FUNCS_ST='$(LIB2FUNCS_ST)' \
|
||||
LIBGCOV='$(LIBGCOV)' \
|
||||
LIB2ADD='$(LIB2ADD)' \
|
||||
LIB2ADD_ST='$(LIB2ADD_ST)' \
|
||||
LIB2ADD_SH='$(LIB2ADD_SH)' \
|
||||
LIB2ADDEH='$(LIB2ADDEH)' \
|
||||
LIB2ADDEHSTATIC='$(LIB2ADDEHSTATIC)' \
|
||||
LIB2ADDEHSHARED='$(LIB2ADDEHSHARED)' \
|
||||
LIB2ADDEHDEP='$(LIB2ADDEHDEP)' \
|
||||
LIBUNWIND='$(LIBUNWIND)' \
|
||||
LIBUNWINDDEP='$(LIBUNWINDDEP)' \
|
||||
SHLIBUNWIND_LINK='$(SHLIBUNWIND_LINK)' \
|
||||
SHLIBUNWIND_INSTALL='$(SHLIBUNWIND_INSTALL)' \
|
||||
FPBIT='$(FPBIT)' \
|
||||
FPBIT_FUNCS='$(FPBIT_FUNCS)' \
|
||||
LIB2_DIVMOD_FUNCS='$(LIB2_DIVMOD_FUNCS)' \
|
||||
@ -1170,8 +1194,8 @@ LIBGCC_DEPS = $(GCC_PASSES) $(LANGUAGES) stmp-int-hdrs $(STMP_FIXPROTO) \
|
||||
libgcc.mk $(srcdir)/libgcc2.c $(srcdir)/libgcov.c $(TCONFIG_H) \
|
||||
$(MACHMODE_H) longlong.h gbl-ctors.h config.status stmp-int-hdrs \
|
||||
tsystem.h $(FPBIT) $(DPBIT) $(TPBIT) $(LIB2ADD) \
|
||||
$(LIB2ADD_ST) $(LIB2ADDEH) $(LIB2ADDEHDEP) $(EXTRA_PARTS) \
|
||||
$(srcdir)/config/$(LIB1ASMSRC) \
|
||||
$(LIB2ADD_ST) $(LIB2ADD_SH) $(LIB2ADDEH) $(LIB2ADDEHDEP) \
|
||||
$(EXTRA_PARTS) $(srcdir)/config/$(LIB1ASMSRC) \
|
||||
$(srcdir)/gcov-io.h $(srcdir)/gcov-io.c gcov-iov.h
|
||||
|
||||
libgcov.a: libgcc.a; @true
|
||||
@ -1578,7 +1602,7 @@ expr.o : expr.c $(CONFIG_H) $(SYSTEM_H) coretypes.h $(TM_H) $(RTL_H) $(TREE_H) f
|
||||
except.h reload.h $(GGC_H) langhooks.h intl.h $(TM_P_H) real.h $(TARGET_H)
|
||||
dojump.o : dojump.c $(CONFIG_H) $(SYSTEM_H) coretypes.h $(TM_H) $(RTL_H) $(TREE_H) \
|
||||
flags.h function.h $(EXPR_H) $(OPTABS_H) $(INSN_ATTR_H) insn-config.h \
|
||||
langhooks.h
|
||||
langhooks.h $(GGC_H) gt-dojump.h
|
||||
builtins.o : builtins.c $(CONFIG_H) $(SYSTEM_H) coretypes.h $(TM_H) $(RTL_H) $(TREE_H)\
|
||||
flags.h $(TARGET_H) function.h $(REGS_H) $(EXPR_H) $(OPTABS_H) insn-config.h \
|
||||
$(RECOG_H) output.h typeclass.h hard-reg-set.h toplev.h hard-reg-set.h \
|
||||
@ -1727,7 +1751,8 @@ dominance.o : dominance.c $(CONFIG_H) $(SYSTEM_H) coretypes.h $(TM_H) $(RTL_H) \
|
||||
et-forest.o : et-forest.c $(CONFIG_H) $(SYSTEM_H) coretypes.h $(TM_H) et-forest.h alloc-pool.h
|
||||
combine.o : combine.c $(CONFIG_H) $(SYSTEM_H) coretypes.h $(TM_H) $(RTL_H) flags.h \
|
||||
function.h insn-config.h $(INSN_ATTR_H) $(REGS_H) $(EXPR_H) \
|
||||
$(BASIC_BLOCK_H) $(RECOG_H) real.h hard-reg-set.h toplev.h $(TM_P_H) $(TREE_H) $(TARGET_H)
|
||||
$(BASIC_BLOCK_H) $(RECOG_H) real.h hard-reg-set.h toplev.h $(TM_P_H) \
|
||||
$(TREE_H) $(TARGET_H) $(PARAMS_H)
|
||||
regclass.o : regclass.c $(CONFIG_H) $(SYSTEM_H) coretypes.h $(TM_H) $(RTL_H) \
|
||||
hard-reg-set.h flags.h $(BASIC_BLOCK_H) $(REGS_H) insn-config.h $(RECOG_H) reload.h \
|
||||
real.h toplev.h function.h output.h $(GGC_H) $(TM_P_H) $(EXPR_H) $(TIMEVAR_H)
|
||||
@ -2060,6 +2085,7 @@ GTFILES = $(srcdir)/input.h $(srcdir)/coretypes.h $(srcdir)/cpplib.h \
|
||||
$(srcdir)/c-common.h $(srcdir)/c-tree.h \
|
||||
$(srcdir)/alias.c $(srcdir)/bitmap.c $(srcdir)/cselib.c $(srcdir)/cgraph.c \
|
||||
$(srcdir)/dbxout.c $(srcdir)/dwarf2out.c $(srcdir)/dwarf2asm.c \
|
||||
$(srcdir)/dojump.c \
|
||||
$(srcdir)/emit-rtl.c $(srcdir)/except.c $(srcdir)/explow.c $(srcdir)/expr.c \
|
||||
$(srcdir)/fold-const.c $(srcdir)/function.c \
|
||||
$(srcdir)/gcse.c $(srcdir)/integrate.c $(srcdir)/lists.c $(srcdir)/optabs.c \
|
||||
@ -2079,7 +2105,7 @@ gt-cgraph.h gt-coverage.h gtype-desc.h gtype-desc.c gt-except.h \
|
||||
gt-function.h gt-integrate.h gt-stmt.h gt-tree.h gt-varasm.h \
|
||||
gt-emit-rtl.h gt-explow.h gt-stor-layout.h gt-regclass.h \
|
||||
gt-lists.h gt-alias.h gt-cselib.h gt-fold-const.h gt-gcse.h \
|
||||
gt-expr.h gt-sdbout.h gt-optabs.h gt-bitmap.h \
|
||||
gt-expr.h gt-sdbout.h gt-optabs.h gt-bitmap.h gt-dojump.h \
|
||||
gt-dwarf2out.h gt-ra-build.h gt-reg-stack.h gt-dwarf2asm.h \
|
||||
gt-dbxout.h gt-c-common.h gt-c-decl.h gt-c-parse.h \
|
||||
gt-c-pragma.h gtype-c.h gt-input.h gt-cfglayout.h \
|
||||
@ -2779,7 +2805,8 @@ mostlyclean: lang.mostlyclean
|
||||
# that don't exist in the distribution.
|
||||
clean: mostlyclean lang.clean
|
||||
-rm -f libgcc.a libgcc_eh.a libgcov.a
|
||||
-rm -f libgcc_s$(SHLIB_EXT) libgcc_s$(SHLIB_EXT).1
|
||||
-rm -f libgcc_s*
|
||||
-rm -f libunwind*
|
||||
-rm -f config.h tconfig.h bconfig.h tm_p.h tm.h
|
||||
-rm -f cs-*
|
||||
-rm -rf libgcc
|
||||
@ -3606,6 +3633,7 @@ stage1-start:
|
||||
-if [ -f collect-ld$(exeext) ] ; then (cd stage1 && $(LN_S) ../collect-ld$(exeext) .) ; else true ; fi
|
||||
-rm -f stage1/libgcc.a stage1/libgcc_eh.a stage1/libgcov.a
|
||||
-rm -f stage1/libgcc_s*$(SHLIB_EXT)
|
||||
-rm -f stage1/libunwind.a stage1/libunwind*$(SHLIB_EXT)
|
||||
-cp libgcc.a stage1
|
||||
-$(RANLIB_FOR_TARGET) stage1/libgcc.a
|
||||
-cp libgcov.a stage1
|
||||
@ -3614,6 +3642,7 @@ stage1-start:
|
||||
$(RANLIB_FOR_TARGET) stage1/libgcc_eh.a; \
|
||||
fi
|
||||
-cp libgcc_s*$(SHLIB_EXT) stage1
|
||||
-cp libunwind.a libunwind*$(SHLIB_EXT) stage1
|
||||
-for f in .. $(EXTRA_MULTILIB_PARTS); do if [ x$${f} != x.. ]; then \
|
||||
cp stage1/$${f} . ; \
|
||||
else true; \
|
||||
@ -3641,6 +3670,7 @@ stage2-start:
|
||||
-if [ -f collect-ld$(exeext) ] ; then (cd stage2 && $(LN_S) ../collect-ld$(exeext) .) ; else true ; fi
|
||||
-rm -f stage2/libgcc.a stage2/libgcov.a stage2/libgcc_eh.a
|
||||
-rm -f stage2/libgcc_s*$(SHLIB_EXT)
|
||||
-rm -f stage2/libunwind.a stage2/libunwind*$(SHLIB_EXT)
|
||||
-cp libgcc.a stage2
|
||||
-$(RANLIB_FOR_TARGET) stage2/libgcc.a
|
||||
-cp libgcov.a stage2
|
||||
@ -3649,6 +3679,7 @@ stage2-start:
|
||||
$(RANLIB_FOR_TARGET) stage2/libgcc_eh.a; \
|
||||
fi
|
||||
-cp libgcc_s*$(SHLIB_EXT) stage2
|
||||
-cp libunwind.a libunwind*$(SHLIB_EXT) stage2
|
||||
-for f in .. $(EXTRA_MULTILIB_PARTS); do if [ x$${f} != x.. ]; then \
|
||||
cp stage2/$${f} . ; \
|
||||
else true; \
|
||||
@ -3672,6 +3703,7 @@ stage3-start:
|
||||
-if [ -f collect-ld$(exeext) ] ; then (cd stage3 && $(LN_S) ../collect-ld$(exeext) .) ; else true ; fi
|
||||
-rm -f stage3/libgcc.a stage3/libgcov.a stage3/libgcc_eh.a
|
||||
-rm -f stage3/libgcc_s*$(SHLIB_EXT)
|
||||
-rm -f stage3/libunwind.a stage3/libunwind*$(SHLIB_EXT)
|
||||
-cp libgcc.a stage3
|
||||
-$(RANLIB_FOR_TARGET) stage3/libgcc.a
|
||||
-cp libgcov.a stage3
|
||||
@ -3680,6 +3712,7 @@ stage3-start:
|
||||
$(RANLIB_FOR_TARGET) stage3/libgcc_eh.a; \
|
||||
fi
|
||||
-cp libgcc_s*$(SHLIB_EXT) stage3
|
||||
-cp libunwind.a libunwind*$(SHLIB_EXT) stage3
|
||||
-for f in .. $(EXTRA_MULTILIB_PARTS); do if [ x$${f} != x.. ]; then \
|
||||
cp stage3/$${f} . ; \
|
||||
else true; \
|
||||
@ -3703,6 +3736,7 @@ stage4-start:
|
||||
-if [ -f collect-ld$(exeext) ] ; then (cd stage4 && $(LN_S) ../collect-ld$(exeext) .) ; else true ; fi
|
||||
-rm -f stage4/libgcc.a stage4/libgcov.a stage4/libgcc_eh.a
|
||||
-rm -f stage4/libgcc_s*$(SHLIB_EXT)
|
||||
-rm -f stage4/libunwind.a stage4/libunwind*$(SHLIB_EXT)
|
||||
-cp libgcc.a stage4
|
||||
-$(RANLIB_FOR_TARGET) stage4/libgcc.a
|
||||
-cp libgcov.a stage4
|
||||
@ -3711,6 +3745,7 @@ stage4-start:
|
||||
$(RANLIB_FOR_TARGET) stage4/libgcc_eh.a; \
|
||||
fi
|
||||
-cp libgcc_s*$(SHLIB_EXT) stage4
|
||||
-cp libunwind.a libunwind*$(SHLIB_EXT) stage4
|
||||
-for f in .. $(EXTRA_MULTILIB_PARTS); do if [ x$${f} != x.. ]; then \
|
||||
cp stage4/$${f} . ; \
|
||||
else true; \
|
||||
@ -3732,6 +3767,7 @@ stageprofile-start:
|
||||
-if [ -f collect-ld$(exeext) ] ; then (cd stageprofile && $(LN_S) ../collect-ld$(exeext) .) ; else true ; fi
|
||||
-rm -f stageprofile/libgcc.a stageprofile/libgcov.a stageprofile/libgcc_eh.a
|
||||
-rm -f stageprofile/libgcc_s*$(SHLIB_EXT)
|
||||
-rm -f stageprofile/libunwind.a stageprofile/libunwind*$(SHLIB_EXT)
|
||||
-cp libgcc.a stageprofile
|
||||
-$(RANLIB_FOR_TARGET) stageprofile/libgcc.a
|
||||
-cp libgcov.a stageprofile
|
||||
@ -3740,6 +3776,7 @@ stageprofile-start:
|
||||
$(RANLIB_FOR_TARGET) stageprofile/libgcc_eh.a; \
|
||||
fi
|
||||
-cp libgcc_s*$(SHLIB_EXT) stageprofile
|
||||
-cp libunwind.a libunwind*$(SHLIB_EXT) stageprofile
|
||||
-for f in .. $(EXTRA_MULTILIB_PARTS); do if [ x$${f} != x.. ]; then \
|
||||
cp stageprofile/$${f} . ; \
|
||||
else true; \
|
||||
@ -3761,6 +3798,7 @@ stagefeedback-start:
|
||||
-if [ -f collect-ld$(exeext) ] ; then (cd stagefeedback && $(LN_S) ../collect-ld$(exeext) .) ; else true ; fi
|
||||
-rm -f stagefeedback/libgcc.a stagefeedback/libgcov.a stagefeedback/libgcc_eh.a
|
||||
-rm -f stagefeedback/libgcc_s*$(SHLIB_EXT)
|
||||
-rm -f stagefeedback/libunwind.a stagefeedback/libunwind*$(SHLIB_EXT)
|
||||
-rm -f *.da
|
||||
-for dir in fixinc po testsuite $(SUBDIRS); \
|
||||
do \
|
||||
@ -3774,6 +3812,7 @@ stagefeedback-start:
|
||||
$(RANLIB_FOR_TARGET) stagefeedback/libgcc_eh.a; \
|
||||
fi
|
||||
-cp libgcc_s*$(SHLIB_EXT) stagefeedback
|
||||
-cp libunwind.a libunwind*$(SHLIB_EXT) stagefeedback
|
||||
-for f in .. $(EXTRA_MULTILIB_PARTS); do if [ x$${f} != x.. ]; then \
|
||||
cp stagefeedback/$${f} . ; \
|
||||
else true; \
|
||||
|
@ -266,6 +266,8 @@ decl_attributes (tree *node, tree attributes, int flags)
|
||||
/* Force a recalculation of mode and size. */
|
||||
DECL_MODE (*node) = VOIDmode;
|
||||
DECL_SIZE (*node) = 0;
|
||||
if (!DECL_USER_ALIGN (*node))
|
||||
DECL_ALIGN (*node) = 0;
|
||||
|
||||
layout_decl (*node, 0);
|
||||
}
|
||||
|
@ -1708,6 +1708,7 @@ expand_builtin_mathfn (tree exp, rtx target, rtx subtarget)
|
||||
narg = save_expr (arg);
|
||||
if (narg != arg)
|
||||
{
|
||||
arg = narg;
|
||||
arglist = build_tree_list (NULL_TREE, arg);
|
||||
exp = build_function_call_expr (fndecl, arglist);
|
||||
}
|
||||
@ -1840,6 +1841,7 @@ expand_builtin_mathfn_2 (tree exp, rtx target, rtx subtarget)
|
||||
narg = save_expr (arg1);
|
||||
if (narg != arg1)
|
||||
{
|
||||
arg1 = narg;
|
||||
temp = build_tree_list (NULL_TREE, narg);
|
||||
stable = false;
|
||||
}
|
||||
@ -1849,6 +1851,7 @@ expand_builtin_mathfn_2 (tree exp, rtx target, rtx subtarget)
|
||||
narg = save_expr (arg0);
|
||||
if (narg != arg0)
|
||||
{
|
||||
arg0 = narg;
|
||||
arglist = tree_cons (NULL_TREE, narg, temp);
|
||||
stable = false;
|
||||
}
|
||||
@ -6581,7 +6584,7 @@ fold_builtin (tree exp)
|
||||
return build_function_call_expr (expfn, arglist);
|
||||
}
|
||||
|
||||
/* Optimize sqrt(pow(x,y)) = pow(x,y*0.5). */
|
||||
/* Optimize sqrt(pow(x,y)) = pow(|x|,y*0.5). */
|
||||
if (flag_unsafe_math_optimizations
|
||||
&& (fcode == BUILT_IN_POW
|
||||
|| fcode == BUILT_IN_POWF
|
||||
@ -6590,8 +6593,11 @@ fold_builtin (tree exp)
|
||||
tree powfn = TREE_OPERAND (TREE_OPERAND (arg, 0), 0);
|
||||
tree arg0 = TREE_VALUE (TREE_OPERAND (arg, 1));
|
||||
tree arg1 = TREE_VALUE (TREE_CHAIN (TREE_OPERAND (arg, 1)));
|
||||
tree narg1 = fold (build (MULT_EXPR, type, arg1,
|
||||
build_real (type, dconsthalf)));
|
||||
tree narg1;
|
||||
if (!tree_expr_nonnegative_p (arg0))
|
||||
arg0 = build1 (ABS_EXPR, type, arg0);
|
||||
narg1 = fold (build (MULT_EXPR, type, arg1,
|
||||
build_real (type, dconsthalf)));
|
||||
arglist = tree_cons (NULL_TREE, arg0,
|
||||
build_tree_list (NULL_TREE, narg1));
|
||||
return build_function_call_expr (powfn, arglist);
|
||||
|
@ -767,7 +767,6 @@ static tree handle_nothrow_attribute (tree *, tree, tree, int, bool *);
|
||||
static tree handle_cleanup_attribute (tree *, tree, tree, int, bool *);
|
||||
static tree handle_warn_unused_result_attribute (tree *, tree, tree, int,
|
||||
bool *);
|
||||
static tree vector_size_helper (tree, tree);
|
||||
|
||||
static void check_function_nonnull (tree, tree);
|
||||
static void check_nonnull_arg (void *, tree, unsigned HOST_WIDE_INT);
|
||||
@ -1138,7 +1137,7 @@ fname_decl (unsigned int rid, tree id)
|
||||
input_line = saved_lineno;
|
||||
}
|
||||
if (!ix && !current_function_decl)
|
||||
pedwarn ("%J'%D' is not defined outside of function scope", decl, decl);
|
||||
pedwarn ("'%D' is not defined outside of function scope", decl);
|
||||
|
||||
return decl;
|
||||
}
|
||||
@ -4643,7 +4642,10 @@ handle_mode_attribute (tree *node, tree name, tree args ATTRIBUTE_UNUSED,
|
||||
else
|
||||
for (j = 0; j < NUM_MACHINE_MODES; j++)
|
||||
if (!strcmp (p, GET_MODE_NAME (j)))
|
||||
mode = (enum machine_mode) j;
|
||||
{
|
||||
mode = (enum machine_mode) j;
|
||||
break;
|
||||
}
|
||||
|
||||
if (mode == VOIDmode)
|
||||
error ("unknown machine mode `%s'", p);
|
||||
@ -4676,8 +4678,44 @@ handle_mode_attribute (tree *node, tree name, tree args ATTRIBUTE_UNUSED,
|
||||
mode);
|
||||
*node = ptr_type;
|
||||
}
|
||||
else if (TREE_CODE (type) == ENUMERAL_TYPE)
|
||||
{
|
||||
/* For enumeral types, copy the precision from the integer
|
||||
type returned above. If not an INTEGER_TYPE, we can't use
|
||||
this mode for this type. */
|
||||
if (TREE_CODE (typefm) != INTEGER_TYPE)
|
||||
{
|
||||
error ("cannot use mode %qs for enumeral types", p);
|
||||
return NULL_TREE;
|
||||
}
|
||||
|
||||
if (!(flags & (int) ATTR_FLAG_TYPE_IN_PLACE))
|
||||
type = build_type_copy (type);
|
||||
|
||||
/* We cannot use layout_type here, because that will attempt
|
||||
to re-layout all variants, corrupting our original. */
|
||||
TYPE_PRECISION (type) = TYPE_PRECISION (typefm);
|
||||
TYPE_MIN_VALUE (type) = TYPE_MIN_VALUE (typefm);
|
||||
TYPE_MAX_VALUE (type) = TYPE_MAX_VALUE (typefm);
|
||||
TYPE_SIZE (type) = TYPE_SIZE (typefm);
|
||||
TYPE_SIZE_UNIT (type) = TYPE_SIZE_UNIT (typefm);
|
||||
TYPE_MODE (type) = TYPE_MODE (typefm);
|
||||
if (!TYPE_USER_ALIGN (type))
|
||||
TYPE_ALIGN (type) = TYPE_ALIGN (typefm);
|
||||
|
||||
*node = type;
|
||||
}
|
||||
else if (VECTOR_MODE_P (mode)
|
||||
? TREE_CODE (type) != TREE_CODE (TREE_TYPE (typefm))
|
||||
: TREE_CODE (type) != TREE_CODE (typefm))
|
||||
|
||||
{
|
||||
error ("mode `%s' applied to inappropriate type", p);
|
||||
return NULL_TREE;
|
||||
}
|
||||
else
|
||||
*node = typefm;
|
||||
*node = typefm;
|
||||
|
||||
/* No need to layout the type here. The caller should do this. */
|
||||
}
|
||||
}
|
||||
@ -5246,57 +5284,11 @@ handle_vector_size_attribute (tree *node, tree name, tree args,
|
||||
}
|
||||
|
||||
/* Build back pointers if needed. */
|
||||
*node = vector_size_helper (*node, new_type);
|
||||
*node = reconstruct_complex_type (*node, new_type);
|
||||
|
||||
return NULL_TREE;
|
||||
}
|
||||
|
||||
/* HACK. GROSS. This is absolutely disgusting. I wish there was a
|
||||
better way.
|
||||
|
||||
If we requested a pointer to a vector, build up the pointers that
|
||||
we stripped off while looking for the inner type. Similarly for
|
||||
return values from functions.
|
||||
|
||||
The argument "type" is the top of the chain, and "bottom" is the
|
||||
new type which we will point to. */
|
||||
|
||||
static tree
|
||||
vector_size_helper (tree type, tree bottom)
|
||||
{
|
||||
tree inner, outer;
|
||||
|
||||
if (POINTER_TYPE_P (type))
|
||||
{
|
||||
inner = vector_size_helper (TREE_TYPE (type), bottom);
|
||||
outer = build_pointer_type (inner);
|
||||
}
|
||||
else if (TREE_CODE (type) == ARRAY_TYPE)
|
||||
{
|
||||
inner = vector_size_helper (TREE_TYPE (type), bottom);
|
||||
outer = build_array_type (inner, TYPE_DOMAIN (type));
|
||||
}
|
||||
else if (TREE_CODE (type) == FUNCTION_TYPE)
|
||||
{
|
||||
inner = vector_size_helper (TREE_TYPE (type), bottom);
|
||||
outer = build_function_type (inner, TYPE_ARG_TYPES (type));
|
||||
}
|
||||
else if (TREE_CODE (type) == METHOD_TYPE)
|
||||
{
|
||||
inner = vector_size_helper (TREE_TYPE (type), bottom);
|
||||
outer = build_method_type_directly (TYPE_METHOD_BASETYPE (type),
|
||||
inner,
|
||||
TYPE_ARG_TYPES (type));
|
||||
}
|
||||
else
|
||||
return bottom;
|
||||
|
||||
TREE_READONLY (outer) = TREE_READONLY (type);
|
||||
TREE_THIS_VOLATILE (outer) = TREE_THIS_VOLATILE (type);
|
||||
|
||||
return outer;
|
||||
}
|
||||
|
||||
/* Handle the "nonnull" attribute. */
|
||||
static tree
|
||||
handle_nonnull_attribute (tree *node, tree name ATTRIBUTE_UNUSED,
|
||||
|
@ -3620,10 +3620,6 @@ grokdeclarator (tree declarator, tree declspecs,
|
||||
}
|
||||
}
|
||||
|
||||
/* Check the type and width of a bit-field. */
|
||||
if (bitfield)
|
||||
check_bitfield_type_and_width (&type, width, orig_name);
|
||||
|
||||
/* Figure out the type qualifiers for the declaration. There are
|
||||
two ways a declaration can become qualified. One is something
|
||||
like `const int i' where the `const' is explicit. Another is
|
||||
@ -3983,7 +3979,17 @@ grokdeclarator (tree declarator, tree declspecs,
|
||||
}
|
||||
else if (TREE_CODE (declarator) == CALL_EXPR)
|
||||
{
|
||||
/* Say it's a definition only for the declarator closest to
|
||||
the identifier, apart possibly from some attributes. */
|
||||
bool really_funcdef = false;
|
||||
tree arg_types;
|
||||
if (funcdef_flag)
|
||||
{
|
||||
tree t = TREE_OPERAND (declarator, 0);
|
||||
while (TREE_CODE (t) == TREE_LIST)
|
||||
t = TREE_VALUE (t);
|
||||
really_funcdef = (TREE_CODE (t) == IDENTIFIER_NODE);
|
||||
}
|
||||
|
||||
/* Declaring a function type.
|
||||
Make sure we have a valid type for the function to return. */
|
||||
@ -4009,11 +4015,7 @@ grokdeclarator (tree declarator, tree declspecs,
|
||||
inner layer of declarator. */
|
||||
|
||||
arg_types = grokparms (TREE_OPERAND (declarator, 1),
|
||||
funcdef_flag
|
||||
/* Say it's a definition
|
||||
only for the CALL_EXPR
|
||||
closest to the identifier. */
|
||||
&& TREE_CODE (TREE_OPERAND (declarator, 0)) == IDENTIFIER_NODE);
|
||||
really_funcdef);
|
||||
/* Type qualifiers before the return type of the function
|
||||
qualify the return type, not the function type. */
|
||||
if (type_quals)
|
||||
@ -4127,6 +4129,10 @@ grokdeclarator (tree declarator, tree declspecs,
|
||||
|
||||
/* Now TYPE has the actual type. */
|
||||
|
||||
/* Check the type and width of a bit-field. */
|
||||
if (bitfield)
|
||||
check_bitfield_type_and_width (&type, width, orig_name);
|
||||
|
||||
/* Did array size calculations overflow? */
|
||||
|
||||
if (TREE_CODE (type) == ARRAY_TYPE
|
||||
@ -5126,7 +5132,7 @@ finish_struct (tree t, tree fieldlist, tree attributes)
|
||||
make it one, warn and turn off the flag. */
|
||||
if (TREE_CODE (t) == UNION_TYPE
|
||||
&& TYPE_TRANSPARENT_UNION (t)
|
||||
&& TYPE_MODE (t) != DECL_MODE (TYPE_FIELDS (t)))
|
||||
&& (!TYPE_FIELDS (t) || TYPE_MODE (t) != DECL_MODE (TYPE_FIELDS (t))))
|
||||
{
|
||||
TYPE_TRANSPARENT_UNION (t) = 0;
|
||||
warning ("union cannot be made transparent");
|
||||
@ -5278,9 +5284,19 @@ finish_enum (tree enumtype, tree values, tree attributes)
|
||||
|
||||
TYPE_MIN_VALUE (enumtype) = minnode;
|
||||
TYPE_MAX_VALUE (enumtype) = maxnode;
|
||||
TYPE_PRECISION (enumtype) = precision;
|
||||
TREE_UNSIGNED (enumtype) = unsign;
|
||||
TYPE_SIZE (enumtype) = 0;
|
||||
|
||||
/* If the precision of the type was specific with an attribute and it
|
||||
was too small, give an error. Otherwise, use it. */
|
||||
if (TYPE_PRECISION (enumtype))
|
||||
{
|
||||
if (precision > TYPE_PRECISION (enumtype))
|
||||
error ("specified mode too small for enumeral values");
|
||||
}
|
||||
else
|
||||
TYPE_PRECISION (enumtype) = precision;
|
||||
|
||||
layout_type (enumtype);
|
||||
|
||||
if (values != error_mark_node)
|
||||
|
@ -2518,9 +2518,27 @@ init_dynamic_asm_fprintf_info (void)
|
||||
length modifier to work, one must have issued: "typedef
|
||||
HOST_WIDE_INT __gcc_host_wide_int__;" in one's source code
|
||||
prior to using that modifier. */
|
||||
if (!(hwi = maybe_get_identifier ("__gcc_host_wide_int__"))
|
||||
|| !(hwi = DECL_ORIGINAL_TYPE (identifier_global_value (hwi))))
|
||||
hwi = maybe_get_identifier ("__gcc_host_wide_int__");
|
||||
if (!hwi)
|
||||
{
|
||||
error ("'__gcc_host_wide_int__' is not defined as a type");
|
||||
return;
|
||||
}
|
||||
hwi = identifier_global_value (hwi);
|
||||
if (!hwi || TREE_CODE (hwi) != TYPE_DECL)
|
||||
{
|
||||
error ("'__gcc_host_wide_int__' is not defined as a type");
|
||||
return;
|
||||
}
|
||||
hwi = DECL_ORIGINAL_TYPE (hwi);
|
||||
if (!hwi)
|
||||
abort ();
|
||||
if (hwi != long_integer_type_node && hwi != long_long_integer_type_node)
|
||||
{
|
||||
error ("'__gcc_host_wide_int__' is not defined as 'long'"
|
||||
" or 'long long'");
|
||||
return;
|
||||
}
|
||||
|
||||
/* Create a new (writable) copy of asm_fprintf_length_specs. */
|
||||
new_asm_fprintf_length_specs = xmemdup (asm_fprintf_length_specs,
|
||||
@ -2563,19 +2581,71 @@ init_dynamic_diag_info (void)
|
||||
However we don't force a hard ICE because we may see only one
|
||||
or the other type. */
|
||||
if ((loc = maybe_get_identifier ("location_t")))
|
||||
loc = TREE_TYPE (identifier_global_value (loc));
|
||||
{
|
||||
loc = identifier_global_value (loc);
|
||||
if (loc)
|
||||
{
|
||||
if (TREE_CODE (loc) != TYPE_DECL)
|
||||
{
|
||||
error ("'location_t' is not defined as a type");
|
||||
loc = 0;
|
||||
}
|
||||
else
|
||||
loc = TREE_TYPE (loc);
|
||||
}
|
||||
}
|
||||
|
||||
/* We need to grab the underlying `union tree_node' so peek into
|
||||
an extra type level. */
|
||||
if ((t = maybe_get_identifier ("tree")))
|
||||
t = TREE_TYPE (TREE_TYPE (identifier_global_value (t)));
|
||||
{
|
||||
t = identifier_global_value (t);
|
||||
if (t)
|
||||
{
|
||||
if (TREE_CODE (t) != TYPE_DECL)
|
||||
{
|
||||
error ("'tree' is not defined as a type");
|
||||
t = 0;
|
||||
}
|
||||
else if (TREE_CODE (TREE_TYPE (t)) != POINTER_TYPE)
|
||||
{
|
||||
error ("'tree' is not defined as a pointer type");
|
||||
t = 0;
|
||||
}
|
||||
else
|
||||
t = TREE_TYPE (TREE_TYPE (t));
|
||||
}
|
||||
}
|
||||
|
||||
/* Find the underlying type for HOST_WIDE_INT. For the %w
|
||||
length modifier to work, one must have issued: "typedef
|
||||
HOST_WIDE_INT __gcc_host_wide_int__;" in one's source code
|
||||
prior to using that modifier. */
|
||||
if ((hwi = maybe_get_identifier ("__gcc_host_wide_int__")))
|
||||
hwi = DECL_ORIGINAL_TYPE (identifier_global_value (hwi));
|
||||
{
|
||||
hwi = identifier_global_value (hwi);
|
||||
if (hwi)
|
||||
{
|
||||
if (TREE_CODE (hwi) != TYPE_DECL)
|
||||
{
|
||||
error ("'__gcc_host_wide_int__' is not defined as a type");
|
||||
hwi = 0;
|
||||
}
|
||||
else
|
||||
{
|
||||
hwi = DECL_ORIGINAL_TYPE (hwi);
|
||||
if (!hwi)
|
||||
abort ();
|
||||
if (hwi != long_integer_type_node
|
||||
&& hwi != long_long_integer_type_node)
|
||||
{
|
||||
error ("'__gcc_host_wide_int__' is not defined"
|
||||
" as 'long' or 'long long'");
|
||||
hwi = 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/* Assign the new data for use. */
|
||||
|
||||
|
@ -186,10 +186,10 @@ defer_opt (enum opt_code code, const char *arg)
|
||||
|
||||
/* Common initialization before parsing options. */
|
||||
unsigned int
|
||||
c_common_init_options (unsigned int argc, const char **argv ATTRIBUTE_UNUSED)
|
||||
c_common_init_options (unsigned int argc, const char **argv)
|
||||
{
|
||||
static const unsigned int lang_flags[] = {CL_C, CL_ObjC, CL_CXX, CL_ObjCXX};
|
||||
unsigned int result;
|
||||
unsigned int i, result;
|
||||
|
||||
/* This is conditionalized only because that is the way the front
|
||||
ends used to do it. Maybe this should be unconditional? */
|
||||
@ -222,17 +222,25 @@ c_common_init_options (unsigned int argc, const char **argv ATTRIBUTE_UNUSED)
|
||||
|
||||
result = lang_flags[c_language];
|
||||
|
||||
/* If potentially preprocessing Fortran we have to accept its front
|
||||
end options since the driver passes most of them through. */
|
||||
#ifdef CL_F77
|
||||
if (c_language == clk_c && argc > 2
|
||||
&& !strcmp (argv[2], "-traditional-cpp" ))
|
||||
if (c_language == clk_c)
|
||||
{
|
||||
permit_fortran_options = true;
|
||||
result |= CL_F77;
|
||||
}
|
||||
for (i = 1; i < argc; i++)
|
||||
{
|
||||
/* If preprocessing assembly language, accept any of the C-family
|
||||
front end options since the driver may pass them through. */
|
||||
if (! strcmp (argv[i], "-lang-asm"))
|
||||
result |= CL_C | CL_ObjC | CL_CXX | CL_ObjCXX;
|
||||
#ifdef CL_F77
|
||||
/* If potentially preprocessing Fortran we have to accept its
|
||||
front end options since the driver may them through. */
|
||||
else if (! strcmp (argv[i], "-traditional-cpp"))
|
||||
{
|
||||
permit_fortran_options = true;
|
||||
result |= CL_F77;
|
||||
}
|
||||
#endif
|
||||
|
||||
}
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
@ -1160,8 +1168,12 @@ c_common_post_options (const char **pfilename)
|
||||
|
||||
*pfilename = this_input_filename
|
||||
= cpp_read_main_file (parse_in, in_fnames[0]);
|
||||
/* Don't do any compilation or preprocessing if there is no input file. */
|
||||
if (this_input_filename == NULL)
|
||||
return true;
|
||||
{
|
||||
errorcount++;
|
||||
return false;
|
||||
}
|
||||
|
||||
if (flag_working_directory
|
||||
&& flag_preprocess_only && ! flag_no_line_commands)
|
||||
@ -1350,11 +1362,13 @@ sanitize_cpp_opts (void)
|
||||
|
||||
/* Disable -dD, -dN and -dI if normal output is suppressed. Allow
|
||||
-dM since at least glibc relies on -M -dM to work. */
|
||||
/* Also, flag_no_output implies flag_no_line_commands, always. */
|
||||
if (flag_no_output)
|
||||
{
|
||||
if (flag_dump_macros != 'M')
|
||||
flag_dump_macros = 0;
|
||||
flag_dump_includes = 0;
|
||||
flag_no_line_commands = 1;
|
||||
}
|
||||
|
||||
cpp_opts->unsigned_char = !flag_signed_char;
|
||||
|
@ -2149,7 +2149,7 @@ compstmt_contents_nonempty:
|
||||
|
||||
compstmt_primary_start:
|
||||
'(' '{'
|
||||
{ if (current_function_decl == 0)
|
||||
{ if (last_tree == NULL)
|
||||
{
|
||||
error ("braced-group within expression allowed only inside a function");
|
||||
YYERROR;
|
||||
|
@ -359,7 +359,7 @@ pp_file_change (const struct line_map *map)
|
||||
{
|
||||
const char *flags = "";
|
||||
|
||||
if (flag_no_line_commands || flag_no_output)
|
||||
if (flag_no_line_commands)
|
||||
return;
|
||||
|
||||
if (map != NULL)
|
||||
|
@ -937,6 +937,9 @@ expand_unreachable_if_stmt (tree t)
|
||||
return true;
|
||||
}
|
||||
|
||||
/* Account for declarations as conditions. */
|
||||
expand_cond (IF_COND (t));
|
||||
|
||||
if (THEN_CLAUSE (t) && ELSE_CLAUSE (t))
|
||||
{
|
||||
n = expand_unreachable_stmt (THEN_CLAUSE (t), 0);
|
||||
@ -969,7 +972,9 @@ expand_unreachable_if_stmt (tree t)
|
||||
/* Expand an unreachable statement list. This function skips all
|
||||
statements preceding the first potentially reachable label and
|
||||
then returns the label (or, in same cases, the statement after
|
||||
one containing the label). */
|
||||
one containing the label). This function returns NULL_TREE if
|
||||
the end of the given statement list is unreachable, and a
|
||||
non-NULL value, possibly error_mark_node, otherwise. */
|
||||
static tree
|
||||
expand_unreachable_stmt (tree t, int warn)
|
||||
{
|
||||
@ -1019,7 +1024,7 @@ expand_unreachable_stmt (tree t, int warn)
|
||||
|
||||
case IF_STMT:
|
||||
if (expand_unreachable_if_stmt (t))
|
||||
return TREE_CHAIN (t);
|
||||
return TREE_CHAIN (t) ? TREE_CHAIN (t) : error_mark_node;
|
||||
break;
|
||||
|
||||
case WHILE_STMT:
|
||||
@ -1027,7 +1032,7 @@ expand_unreachable_stmt (tree t, int warn)
|
||||
no need to rotate the loop, instead the WHILE_STMT can be
|
||||
expanded like a DO_STMT. */
|
||||
genrtl_do_stmt_1 (WHILE_COND (t), WHILE_BODY (t));
|
||||
return TREE_CHAIN (t);
|
||||
return TREE_CHAIN (t) ? TREE_CHAIN (t) : error_mark_node;
|
||||
|
||||
case COMPOUND_STMT:
|
||||
{
|
||||
@ -1036,7 +1041,7 @@ expand_unreachable_stmt (tree t, int warn)
|
||||
if (n != NULL_TREE)
|
||||
{
|
||||
expand_stmt (n);
|
||||
return TREE_CHAIN (t);
|
||||
return TREE_CHAIN (t) ? TREE_CHAIN (t) : error_mark_node;
|
||||
}
|
||||
warn = false;
|
||||
break;
|
||||
|
@ -647,7 +647,7 @@ same_translation_unit_p (tree t1, tree t2)
|
||||
while (t2 && TREE_CODE (t2) != TRANSLATION_UNIT_DECL)
|
||||
switch (TREE_CODE_CLASS (TREE_CODE (t2)))
|
||||
{
|
||||
case 'd': t2 = DECL_CONTEXT (t1); break;
|
||||
case 'd': t2 = DECL_CONTEXT (t2); break;
|
||||
case 't': t2 = TYPE_CONTEXT (t2); break;
|
||||
case 'b': t2 = BLOCK_SUPERCONTEXT (t2); break;
|
||||
default: abort ();
|
||||
@ -1320,26 +1320,6 @@ build_component_ref (tree datum, tree component)
|
||||
tree field = NULL;
|
||||
tree ref;
|
||||
|
||||
/* If DATUM is a COMPOUND_EXPR, move our reference inside it.
|
||||
If pedantic ensure that the arguments are not lvalues; otherwise,
|
||||
if the component is an array, it would wrongly decay to a pointer in
|
||||
C89 mode.
|
||||
We cannot do this with a COND_EXPR, because in a conditional expression
|
||||
the default promotions are applied to both sides, and this would yield
|
||||
the wrong type of the result; for example, if the components have
|
||||
type "char". */
|
||||
switch (TREE_CODE (datum))
|
||||
{
|
||||
case COMPOUND_EXPR:
|
||||
{
|
||||
tree value = build_component_ref (TREE_OPERAND (datum, 1), component);
|
||||
return build (COMPOUND_EXPR, TREE_TYPE (value),
|
||||
TREE_OPERAND (datum, 0), pedantic_non_lvalue (value));
|
||||
}
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
/* See if there is a field or component with name COMPONENT. */
|
||||
|
||||
if (code == RECORD_TYPE || code == UNION_TYPE)
|
||||
@ -4117,18 +4097,32 @@ digest_init (tree type, tree init, int require_constant)
|
||||
/* Build a VECTOR_CST from a *constant* vector constructor. If the
|
||||
vector constructor is not constant (e.g. {1,2,3,foo()}) then punt
|
||||
below and handle as a constructor. */
|
||||
if (code == VECTOR_TYPE
|
||||
&& comptypes (TREE_TYPE (inside_init), type, COMPARE_STRICT)
|
||||
&& TREE_CONSTANT (inside_init))
|
||||
{
|
||||
if (TREE_CODE (inside_init) == VECTOR_CST
|
||||
&& comptypes (TYPE_MAIN_VARIANT (TREE_TYPE (inside_init)),
|
||||
TYPE_MAIN_VARIANT (type),
|
||||
COMPARE_STRICT))
|
||||
return inside_init;
|
||||
else
|
||||
return build_vector (type, CONSTRUCTOR_ELTS (inside_init));
|
||||
}
|
||||
if (code == VECTOR_TYPE
|
||||
&& comptypes (TREE_TYPE (inside_init), type, COMPARE_STRICT)
|
||||
&& TREE_CONSTANT (inside_init))
|
||||
{
|
||||
if (TREE_CODE (inside_init) == VECTOR_CST
|
||||
&& comptypes (TYPE_MAIN_VARIANT (TREE_TYPE (inside_init)),
|
||||
TYPE_MAIN_VARIANT (type),
|
||||
COMPARE_STRICT))
|
||||
return inside_init;
|
||||
|
||||
if (TREE_CODE (inside_init) == CONSTRUCTOR)
|
||||
{
|
||||
tree link;
|
||||
|
||||
/* Iterate through elements and check if all constructor
|
||||
elements are *_CSTs. */
|
||||
for (link = CONSTRUCTOR_ELTS (inside_init);
|
||||
link;
|
||||
link = TREE_CHAIN (link))
|
||||
if (TREE_CODE_CLASS (TREE_CODE (TREE_VALUE (link))) != 'c')
|
||||
break;
|
||||
|
||||
if (link == NULL)
|
||||
return build_vector (type, CONSTRUCTOR_ELTS (inside_init));
|
||||
}
|
||||
}
|
||||
|
||||
/* Any type can be initialized
|
||||
from an expression of the same type, optionally with braces. */
|
||||
@ -6571,6 +6565,14 @@ c_finish_case (void)
|
||||
{
|
||||
struct c_switch *cs = switch_stack;
|
||||
|
||||
/* If we've not seen any case labels (or a default), we may still
|
||||
need to chain any statements that were seen as the SWITCH_BODY. */
|
||||
if (SWITCH_BODY (cs->switch_stmt) == NULL)
|
||||
{
|
||||
SWITCH_BODY (cs->switch_stmt) = TREE_CHAIN (cs->switch_stmt);
|
||||
TREE_CHAIN (cs->switch_stmt) = NULL_TREE;
|
||||
}
|
||||
|
||||
/* Rechain the next statements to the SWITCH_STMT. */
|
||||
last_tree = cs->switch_stmt;
|
||||
|
||||
|
@ -405,7 +405,7 @@ Give strings the type \"array of char\"
|
||||
|
||||
ansi
|
||||
C ObjC C++ ObjC++
|
||||
A synonym for -std=c89. In a future version of GCC it will become synonymous with -std=c99 instead
|
||||
A synonym for -std=c89 (for C) or -std=c++98 (for C++).
|
||||
|
||||
d
|
||||
C ObjC C++ ObjC++ Joined
|
||||
@ -788,7 +788,7 @@ Deprecated in favor of -std=gnu99
|
||||
|
||||
std=iso9899:1990
|
||||
C ObjC
|
||||
Deprecated in favor of -std=c89
|
||||
Conform to the ISO 1990 C standard
|
||||
|
||||
std=iso9899:199409
|
||||
C ObjC
|
||||
@ -796,11 +796,11 @@ Conform to the ISO 1990 C standard as amended in 1994
|
||||
|
||||
std=iso9899:1999
|
||||
C ObjC
|
||||
Deprecated in favor of -std=c99
|
||||
Conform to the ISO 1999 C standard
|
||||
|
||||
std=iso9899:199x
|
||||
C ObjC
|
||||
Deprecated in favor of -std=c99
|
||||
Deprecated in favor of -std=iso9899:1999
|
||||
|
||||
traditional-cpp
|
||||
C ObjC C++ ObjC++
|
||||
|
@ -1719,8 +1719,8 @@ load_register_parameters (struct arg_data *args, int num_actuals,
|
||||
use_group_regs (call_fusage, reg);
|
||||
else if (nregs == -1)
|
||||
use_reg (call_fusage, reg);
|
||||
else
|
||||
use_regs (call_fusage, REGNO (reg), nregs == 0 ? 1 : nregs);
|
||||
else if (nregs > 0)
|
||||
use_regs (call_fusage, REGNO (reg), nregs);
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -2730,10 +2730,14 @@ expand_call (tree exp, rtx target, int ignore)
|
||||
Also, do all pending adjustments now if there is any chance
|
||||
this might be a call to alloca or if we are expanding a sibling
|
||||
call sequence or if we are calling a function that is to return
|
||||
with stack pointer depressed. */
|
||||
with stack pointer depressed.
|
||||
Also do the adjustments before a throwing call, otherwise
|
||||
exception handling can fail; PR 19225. */
|
||||
if (pending_stack_adjust >= 32
|
||||
|| (pending_stack_adjust > 0
|
||||
&& (flags & (ECF_MAY_BE_ALLOCA | ECF_SP_DEPRESSED)))
|
||||
|| (pending_stack_adjust > 0
|
||||
&& flag_exceptions && !(flags & ECF_NOTHROW))
|
||||
|| pass == 0)
|
||||
do_pending_stack_adjust ();
|
||||
|
||||
|
@ -865,6 +865,18 @@ fixup_fallthru_exit_predecessor (void)
|
||||
{
|
||||
basic_block c = ENTRY_BLOCK_PTR->next_bb;
|
||||
|
||||
/* If the very first block is the one with the fall-through exit
|
||||
edge, we have to split that block. */
|
||||
if (c == bb)
|
||||
{
|
||||
bb = split_block (bb, NULL)->dest;
|
||||
cfg_layout_initialize_rbi (bb);
|
||||
bb->rbi->next = c->rbi->next;
|
||||
c->rbi->next = bb;
|
||||
bb->rbi->footer = c->rbi->footer;
|
||||
c->rbi->footer = NULL;
|
||||
}
|
||||
|
||||
while (c->rbi->next != bb)
|
||||
c = c->rbi->next;
|
||||
|
||||
|
@ -483,9 +483,21 @@ rtl_split_block (basic_block bb, void *insnp)
|
||||
edge e;
|
||||
rtx insn = insnp;
|
||||
|
||||
/* There is no point splitting the block after its end. */
|
||||
if (BB_END (bb) == insn)
|
||||
return 0;
|
||||
if (!insn)
|
||||
{
|
||||
insn = first_insn_after_basic_block_note (bb);
|
||||
|
||||
if (insn)
|
||||
insn = PREV_INSN (insn);
|
||||
else
|
||||
insn = get_last_insn ();
|
||||
}
|
||||
|
||||
/* We probably should check type of the insn so that we do not create
|
||||
inconsistent cfg. It is checked in verify_flow_info anyway, so do not
|
||||
bother. */
|
||||
if (insn == BB_END (bb))
|
||||
emit_note_after (NOTE_INSN_DELETED, insn);
|
||||
|
||||
/* Create the new basic block. */
|
||||
new_bb = create_basic_block (NEXT_INSN (insn), BB_END (bb), bb);
|
||||
@ -2711,6 +2723,18 @@ cfg_layout_split_edge (edge e)
|
||||
new_bb->count = e->count;
|
||||
new_bb->frequency = EDGE_FREQUENCY (e);
|
||||
|
||||
/* ??? This info is likely going to be out of date very soon, but we must
|
||||
create it to avoid getting an ICE later. */
|
||||
if (e->dest->global_live_at_start)
|
||||
{
|
||||
new_bb->global_live_at_start = OBSTACK_ALLOC_REG_SET (&flow_obstack);
|
||||
new_bb->global_live_at_end = OBSTACK_ALLOC_REG_SET (&flow_obstack);
|
||||
COPY_REG_SET (new_bb->global_live_at_start,
|
||||
e->dest->global_live_at_start);
|
||||
COPY_REG_SET (new_bb->global_live_at_end,
|
||||
e->dest->global_live_at_start);
|
||||
}
|
||||
|
||||
new_e = make_edge (new_bb, e->dest, EDGE_FALLTHRU);
|
||||
new_e->probability = REG_BR_PROB_BASE;
|
||||
new_e->count = e->count;
|
||||
|
@ -189,6 +189,7 @@ static int strip_flag; /* true if -s */
|
||||
#ifdef COLLECT_EXPORT_LIST
|
||||
static int export_flag; /* true if -bE */
|
||||
static int aix64_flag; /* true if -b64 */
|
||||
static int aixrtl_flag; /* true if -brtl */
|
||||
#endif
|
||||
|
||||
int debug; /* true if -debug */
|
||||
@ -246,7 +247,6 @@ static struct path_prefix cmdline_lib_dirs; /* directories specified with -L */
|
||||
static struct path_prefix libpath_lib_dirs; /* directories in LIBPATH */
|
||||
static struct path_prefix *libpaths[3] = {&cmdline_lib_dirs,
|
||||
&libpath_lib_dirs, NULL};
|
||||
static const char *const libexts[3] = {"a", "so", NULL}; /* possible library extensions */
|
||||
#endif
|
||||
|
||||
static void handler (int);
|
||||
@ -1080,6 +1080,8 @@ main (int argc, char **argv)
|
||||
export_flag = 1;
|
||||
else if (arg[2] == '6' && arg[3] == '4')
|
||||
aix64_flag = 1;
|
||||
else if (arg[2] == 'r' && arg[3] == 't' && arg[4] == 'l')
|
||||
aixrtl_flag = 1;
|
||||
break;
|
||||
#endif
|
||||
|
||||
@ -2823,6 +2825,8 @@ resolve_lib_name (const char *name)
|
||||
{
|
||||
char *lib_buf;
|
||||
int i, j, l = 0;
|
||||
/* Library extensions for AIX dynamic linking. */
|
||||
const char * const libexts[2] = {"a", "so"};
|
||||
|
||||
for (i = 0; libpaths[i]; i++)
|
||||
if (libpaths[i]->max_len > l)
|
||||
@ -2841,14 +2845,15 @@ resolve_lib_name (const char *name)
|
||||
const char *p = "";
|
||||
if (list->prefix[strlen(list->prefix)-1] != '/')
|
||||
p = "/";
|
||||
for (j = 0; libexts[j]; j++)
|
||||
for (j = 0; j < 2; j++)
|
||||
{
|
||||
sprintf (lib_buf, "%s%slib%s.%s",
|
||||
list->prefix, p, name, libexts[j]);
|
||||
if (debug) fprintf (stderr, "searching for: %s\n", lib_buf);
|
||||
list->prefix, p, name,
|
||||
libexts[(j + aixrtl_flag) % 2]);
|
||||
if (debug) fprintf (stderr, "searching for: %s\n", lib_buf);
|
||||
if (file_exists (lib_buf))
|
||||
{
|
||||
if (debug) fprintf (stderr, "found: %s\n", lib_buf);
|
||||
if (debug) fprintf (stderr, "found: %s\n", lib_buf);
|
||||
return (lib_buf);
|
||||
}
|
||||
}
|
||||
|
@ -90,6 +90,7 @@ Software Foundation, 59 Temple Place - Suite 330, Boston, MA
|
||||
#include "real.h"
|
||||
#include "toplev.h"
|
||||
#include "target.h"
|
||||
#include "params.h"
|
||||
|
||||
#ifndef SHIFT_COUNT_TRUNCATED
|
||||
#define SHIFT_COUNT_TRUNCATED 0
|
||||
@ -3417,10 +3418,10 @@ subst (rtx x, rtx from, rtx to, int in_dest, int unique_copy)
|
||||
/* If this is a register being set, ignore it. */
|
||||
new = XEXP (x, i);
|
||||
if (in_dest
|
||||
&& (code == SUBREG || code == STRICT_LOW_PART
|
||||
|| code == ZERO_EXTRACT)
|
||||
&& i == 0
|
||||
&& GET_CODE (new) == REG)
|
||||
&& (((code == SUBREG || code == ZERO_EXTRACT)
|
||||
&& GET_CODE (new) == REG)
|
||||
|| code == STRICT_LOW_PART))
|
||||
;
|
||||
|
||||
else if (COMBINE_RTX_EQUAL_P (XEXP (x, i), from))
|
||||
@ -3715,27 +3716,28 @@ combine_simplify_rtx (rtx x, enum machine_mode op0_mode, int last,
|
||||
temp = simplify_unary_operation (code, mode, XEXP (x, 0), op0_mode);
|
||||
break;
|
||||
case '<':
|
||||
{
|
||||
enum machine_mode cmp_mode = GET_MODE (XEXP (x, 0));
|
||||
if (cmp_mode == VOIDmode)
|
||||
{
|
||||
cmp_mode = GET_MODE (XEXP (x, 1));
|
||||
if (cmp_mode == VOIDmode)
|
||||
cmp_mode = op0_mode;
|
||||
}
|
||||
temp = simplify_relational_operation (code, cmp_mode,
|
||||
XEXP (x, 0), XEXP (x, 1));
|
||||
}
|
||||
#ifdef FLOAT_STORE_FLAG_VALUE
|
||||
if (temp != 0 && GET_MODE_CLASS (mode) == MODE_FLOAT)
|
||||
if (! VECTOR_MODE_P (mode))
|
||||
{
|
||||
if (temp == const0_rtx)
|
||||
temp = CONST0_RTX (mode);
|
||||
else
|
||||
temp = CONST_DOUBLE_FROM_REAL_VALUE (FLOAT_STORE_FLAG_VALUE (mode),
|
||||
mode);
|
||||
}
|
||||
enum machine_mode cmp_mode = GET_MODE (XEXP (x, 0));
|
||||
if (cmp_mode == VOIDmode)
|
||||
{
|
||||
cmp_mode = GET_MODE (XEXP (x, 1));
|
||||
if (cmp_mode == VOIDmode)
|
||||
cmp_mode = op0_mode;
|
||||
}
|
||||
temp = simplify_relational_operation (code, cmp_mode,
|
||||
XEXP (x, 0), XEXP (x, 1));
|
||||
#ifdef FLOAT_STORE_FLAG_VALUE
|
||||
if (temp != 0 && GET_MODE_CLASS (mode) == MODE_FLOAT)
|
||||
{
|
||||
if (temp == const0_rtx)
|
||||
temp = CONST0_RTX (mode);
|
||||
else
|
||||
temp = CONST_DOUBLE_FROM_REAL_VALUE
|
||||
(FLOAT_STORE_FLAG_VALUE (mode), mode);
|
||||
}
|
||||
#endif
|
||||
}
|
||||
break;
|
||||
case 'c':
|
||||
case '2':
|
||||
@ -10019,13 +10021,8 @@ gen_lowpart_for_combine (enum machine_mode mode, rtx x)
|
||||
|
||||
result = gen_lowpart_common (mode, x);
|
||||
#ifdef CANNOT_CHANGE_MODE_CLASS
|
||||
if (result != 0
|
||||
&& GET_CODE (result) == SUBREG
|
||||
&& GET_CODE (SUBREG_REG (result)) == REG
|
||||
&& REGNO (SUBREG_REG (result)) >= FIRST_PSEUDO_REGISTER)
|
||||
bitmap_set_bit (&subregs_of_mode, REGNO (SUBREG_REG (result))
|
||||
* MAX_MACHINE_MODE
|
||||
+ GET_MODE (result));
|
||||
if (result != 0 && GET_CODE (result) == SUBREG)
|
||||
record_subregs_of_mode (result);
|
||||
#endif
|
||||
|
||||
if (result)
|
||||
@ -10692,34 +10689,61 @@ simplify_comparison (enum rtx_code code, rtx *pop0, rtx *pop1)
|
||||
break;
|
||||
|
||||
case SUBREG:
|
||||
/* Check for the case where we are comparing A - C1 with C2,
|
||||
both constants are smaller than 1/2 the maximum positive
|
||||
value in MODE, and the comparison is equality or unsigned.
|
||||
In that case, if A is either zero-extended to MODE or has
|
||||
sufficient sign bits so that the high-order bit in MODE
|
||||
is a copy of the sign in the inner mode, we can prove that it is
|
||||
safe to do the operation in the wider mode. This simplifies
|
||||
many range checks. */
|
||||
/* Check for the case where we are comparing A - C1 with C2, that is
|
||||
|
||||
(subreg:MODE (plus (A) (-C1))) op (C2)
|
||||
|
||||
with C1 a constant, and try to lift the SUBREG, i.e. to do the
|
||||
comparison in the wider mode. One of the following two conditions
|
||||
must be true in order for this to be valid:
|
||||
|
||||
1. The mode extension results in the same bit pattern being added
|
||||
on both sides and the comparison is equality or unsigned. As
|
||||
C2 has been truncated to fit in MODE, the pattern can only be
|
||||
all 0s or all 1s.
|
||||
|
||||
2. The mode extension results in the sign bit being copied on
|
||||
each side.
|
||||
|
||||
The difficulty here is that we have predicates for A but not for
|
||||
(A - C1) so we need to check that C1 is within proper bounds so
|
||||
as to perturbate A as little as possible. */
|
||||
|
||||
if (mode_width <= HOST_BITS_PER_WIDE_INT
|
||||
&& subreg_lowpart_p (op0)
|
||||
&& GET_MODE_BITSIZE (GET_MODE (SUBREG_REG (op0))) > mode_width
|
||||
&& GET_CODE (SUBREG_REG (op0)) == PLUS
|
||||
&& GET_CODE (XEXP (SUBREG_REG (op0), 1)) == CONST_INT
|
||||
&& INTVAL (XEXP (SUBREG_REG (op0), 1)) < 0
|
||||
&& (-INTVAL (XEXP (SUBREG_REG (op0), 1))
|
||||
< (HOST_WIDE_INT) (GET_MODE_MASK (mode) / 2))
|
||||
&& (unsigned HOST_WIDE_INT) const_op < GET_MODE_MASK (mode) / 2
|
||||
&& (0 == (nonzero_bits (XEXP (SUBREG_REG (op0), 0),
|
||||
GET_MODE (SUBREG_REG (op0)))
|
||||
& ~GET_MODE_MASK (mode))
|
||||
|| (num_sign_bit_copies (XEXP (SUBREG_REG (op0), 0),
|
||||
GET_MODE (SUBREG_REG (op0)))
|
||||
> (unsigned int)
|
||||
(GET_MODE_BITSIZE (GET_MODE (SUBREG_REG (op0)))
|
||||
- GET_MODE_BITSIZE (mode)))))
|
||||
&& GET_CODE (XEXP (SUBREG_REG (op0), 1)) == CONST_INT)
|
||||
{
|
||||
op0 = SUBREG_REG (op0);
|
||||
continue;
|
||||
enum machine_mode inner_mode = GET_MODE (SUBREG_REG (op0));
|
||||
rtx a = XEXP (SUBREG_REG (op0), 0);
|
||||
HOST_WIDE_INT c1 = -INTVAL (XEXP (SUBREG_REG (op0), 1));
|
||||
|
||||
if ((c1 > 0
|
||||
&& (unsigned HOST_WIDE_INT) c1
|
||||
< (unsigned HOST_WIDE_INT) 1 << (mode_width - 1)
|
||||
&& (equality_comparison_p || unsigned_comparison_p)
|
||||
/* (A - C1) zero-extends if it is positive and sign-extends
|
||||
if it is negative, C2 both zero- and sign-extends. */
|
||||
&& ((0 == (nonzero_bits (a, inner_mode)
|
||||
& ~GET_MODE_MASK (mode))
|
||||
&& const_op >= 0)
|
||||
/* (A - C1) sign-extends if it is positive and 1-extends
|
||||
if it is negative, C2 both sign- and 1-extends. */
|
||||
|| (num_sign_bit_copies (a, inner_mode)
|
||||
> (unsigned int) (GET_MODE_BITSIZE (inner_mode)
|
||||
- mode_width)
|
||||
&& const_op < 0)))
|
||||
|| ((unsigned HOST_WIDE_INT) c1
|
||||
< (unsigned HOST_WIDE_INT) 1 << (mode_width - 2)
|
||||
/* (A - C1) always sign-extends, like C2. */
|
||||
&& num_sign_bit_copies (a, inner_mode)
|
||||
> (unsigned int) (GET_MODE_BITSIZE (inner_mode)
|
||||
- mode_width - 1)))
|
||||
{
|
||||
op0 = SUBREG_REG (op0);
|
||||
continue;
|
||||
}
|
||||
}
|
||||
|
||||
/* If the inner mode is narrower and we are extracting the low part,
|
||||
@ -11357,6 +11381,47 @@ reversed_comparison (rtx exp, enum machine_mode mode, rtx op0, rtx op1)
|
||||
return gen_binary (reversed_code, mode, op0, op1);
|
||||
}
|
||||
|
||||
/* Utility function for record_value_for_reg. Count number of
|
||||
rtxs in X. */
|
||||
static int
|
||||
count_rtxs (rtx x)
|
||||
{
|
||||
enum rtx_code code = GET_CODE (x);
|
||||
const char *fmt;
|
||||
int i, ret = 1;
|
||||
|
||||
if (GET_RTX_CLASS (code) == '2'
|
||||
|| GET_RTX_CLASS (code) == 'c')
|
||||
{
|
||||
rtx x0 = XEXP (x, 0);
|
||||
rtx x1 = XEXP (x, 1);
|
||||
|
||||
if (x0 == x1)
|
||||
return 1 + 2 * count_rtxs (x0);
|
||||
|
||||
if ((GET_RTX_CLASS (GET_CODE (x1)) == '2'
|
||||
|| GET_RTX_CLASS (GET_CODE (x1)) == 'c')
|
||||
&& (x0 == XEXP (x1, 0) || x0 == XEXP (x1, 1)))
|
||||
return 2 + 2 * count_rtxs (x0)
|
||||
+ count_rtxs (x == XEXP (x1, 0)
|
||||
? XEXP (x1, 1) : XEXP (x1, 0));
|
||||
|
||||
if ((GET_RTX_CLASS (GET_CODE (x0)) == '2'
|
||||
|| GET_RTX_CLASS (GET_CODE (x0)) == 'c')
|
||||
&& (x1 == XEXP (x0, 0) || x1 == XEXP (x0, 1)))
|
||||
return 2 + 2 * count_rtxs (x1)
|
||||
+ count_rtxs (x == XEXP (x0, 0)
|
||||
? XEXP (x0, 1) : XEXP (x0, 0));
|
||||
}
|
||||
|
||||
fmt = GET_RTX_FORMAT (code);
|
||||
for (i = GET_RTX_LENGTH (code) - 1; i >= 0; i--)
|
||||
if (fmt[i] == 'e')
|
||||
ret += count_rtxs (XEXP (x, i));
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
/* Utility function for following routine. Called when X is part of a value
|
||||
being stored into reg_last_set_value. Sets reg_last_set_table_tick
|
||||
for each register mentioned. Similar to mention_regs in cse.c */
|
||||
@ -11463,6 +11528,13 @@ record_value_for_reg (rtx reg, rtx insn, rtx value)
|
||||
&& GET_CODE (XEXP (tem, 0)) == CLOBBER
|
||||
&& GET_CODE (XEXP (tem, 1)) == CLOBBER)
|
||||
tem = XEXP (tem, 0);
|
||||
else if (count_occurrences (value, reg, 1) >= 2)
|
||||
{
|
||||
/* If there are two or more occurrences of REG in VALUE,
|
||||
prevent the value from growing too much. */
|
||||
if (count_rtxs (tem) > MAX_LAST_VALUE_RTL)
|
||||
tem = gen_rtx_CLOBBER (GET_MODE (tem), const0_rtx);
|
||||
}
|
||||
|
||||
value = replace_rtx (copy_rtx (value), reg, tem);
|
||||
}
|
||||
|
@ -28,7 +28,7 @@ Display this information
|
||||
|
||||
-param
|
||||
Common Separate
|
||||
--param <param>=<value> Set paramter <param> to value. See below for a complete list of parameters
|
||||
--param <param>=<value> Set parameter <param> to value. See below for a complete list of parameters
|
||||
|
||||
-target-help
|
||||
Common
|
||||
|
@ -244,6 +244,7 @@ esac
|
||||
# machines.
|
||||
tm_p_file=
|
||||
cpu_type=`echo ${target} | sed 's/-.*$//'`
|
||||
cpu_is_64bit=
|
||||
case ${target} in
|
||||
alpha*-*-*)
|
||||
cpu_type=alpha
|
||||
@ -300,6 +301,11 @@ powerpc*-*-*)
|
||||
cpu_type=rs6000
|
||||
extra_headers="ppc-asm.h altivec.h spe.h"
|
||||
need_64bit_hwint=yes
|
||||
case x$with_cpu in
|
||||
xpowerpc64|xdefault64|x6[23]0|x970|xG5|xpower[345]|xrs64a)
|
||||
cpu_is_64bit=yes
|
||||
;;
|
||||
esac
|
||||
;;
|
||||
rs6000*-*-*)
|
||||
need_64bit_hwint=yes
|
||||
@ -680,7 +686,7 @@ arm*-*-ecos-elf)
|
||||
;;
|
||||
arm*-*-rtems*)
|
||||
tm_file="dbxelf.h elfos.h arm/unknown-elf.h arm/elf.h arm/aout.h arm/arm.h arm/rtems-elf.h rtems.h"
|
||||
tmake_file="arm/t-arm-elf t-rtems"
|
||||
tmake_file="arm/t-arm-elf t-rtems arm/t-rtems"
|
||||
;;
|
||||
arm*-*-elf | ep9312-*-elf)
|
||||
tm_file="dbxelf.h elfos.h arm/unknown-elf.h arm/elf.h arm/aout.h arm/arm.h"
|
||||
@ -700,12 +706,16 @@ arm*-*-kaos*)
|
||||
tm_file="dbxelf.h elfos.h arm/unknown-elf.h arm/elf.h arm/aout.h arm/arm.h kaos.h arm/kaos-arm.h"
|
||||
tmake_file=arm/t-arm-elf
|
||||
;;
|
||||
avr-*-rtems*)
|
||||
tm_file="avr/avr.h dbxelf.h avr/rtems.h rtems.h"
|
||||
tmake_file="avr/t-avr t-rtems avr/t-rtems"
|
||||
;;
|
||||
avr-*-*)
|
||||
tm_file="avr/avr.h dbxelf.h"
|
||||
use_fixproto=yes
|
||||
;;
|
||||
c4x-*-rtems* | tic4x-*-rtems*)
|
||||
tmake_file="c4x/t-c4x t-rtems"
|
||||
tmake_file="c4x/t-c4x t-rtems c4x/t-rtems"
|
||||
tm_file="c4x/c4x.h c4x/rtems.h rtems.h"
|
||||
c_target_objs="c4x-c.o"
|
||||
cxx_target_objs="c4x-c.o"
|
||||
@ -1257,12 +1267,12 @@ ia64*-*-freebsd*)
|
||||
;;
|
||||
ia64*-*-linux*)
|
||||
tm_file="${tm_file} dbxelf.h elfos.h svr4.h linux.h ia64/sysv4.h ia64/linux.h"
|
||||
tmake_file="t-slibgcc-elf-ver t-linux ia64/t-ia64 ia64/t-glibc"
|
||||
tmake_file="t-slibgcc-elf-ver t-linux ia64/t-ia64 t-libunwind ia64/t-glibc"
|
||||
if test x$with_system_libunwind != xyes ; then
|
||||
tmake_file="${tmake_file} t-libunwind-elf ia64/t-glibc-libunwind"
|
||||
fi
|
||||
target_cpu_default="MASK_GNU_AS|MASK_GNU_LD"
|
||||
extra_parts="crtbegin.o crtend.o crtbeginS.o crtendS.o crtfastmath.o"
|
||||
if test x"$use_libunwind_exceptions" = xyes; then
|
||||
tmake_file="$tmake_file t-libunwind"
|
||||
fi
|
||||
;;
|
||||
ia64*-*-hpux*)
|
||||
tm_file="${tm_file} dbxelf.h elfos.h svr4.h ia64/sysv4.h ia64/hpux.h"
|
||||
@ -1678,20 +1688,16 @@ pdp11-*-bsd)
|
||||
pdp11-*-*)
|
||||
use_fixproto=yes
|
||||
;;
|
||||
avr-*-*)
|
||||
use_fixproto=yes
|
||||
;;
|
||||
# port not yet contributed
|
||||
#powerpc-*-openbsd*)
|
||||
# tmake_file="${tmake_file} rs6000/t-fprules "
|
||||
# extra_headers=
|
||||
# ;;
|
||||
powerpc64-*-linux*)
|
||||
tm_file="rs6000/biarch64.h ${tm_file} dbxelf.h elfos.h svr4.h freebsd-spec.h rs6000/sysv4.h"
|
||||
case x$with_cpu in
|
||||
x|xpowerpc64|xdefault64) tm_file="${tm_file} rs6000/default64.h";;
|
||||
esac
|
||||
tm_file="${tm_file} rs6000/linux64.h"
|
||||
tm_file="${tm_file} dbxelf.h elfos.h svr4.h freebsd-spec.h rs6000/sysv4.h"
|
||||
test x$with_cpu != x || cpu_is_64bit=yes
|
||||
test x$cpu_is_64bit != xyes || tm_file="${tm_file} rs6000/default64.h"
|
||||
tm_file="rs6000/biarch64.h ${tm_file} rs6000/linux64.h"
|
||||
tmake_file="rs6000/t-fprules t-slibgcc-elf-ver t-linux rs6000/t-ppccomm rs6000/t-linux64"
|
||||
;;
|
||||
powerpc64-*-gnu*)
|
||||
@ -1765,8 +1771,20 @@ powerpc-*-linux*spe*)
|
||||
tmake_file="rs6000/t-fprules rs6000/t-ppcos t-slibgcc-elf-ver t-linux rs6000/t-ppccomm"
|
||||
;;
|
||||
powerpc-*-linux*)
|
||||
tm_file="${tm_file} dbxelf.h elfos.h svr4.h freebsd-spec.h rs6000/sysv4.h rs6000/linux.h"
|
||||
tm_file="${tm_file} dbxelf.h elfos.h svr4.h freebsd-spec.h rs6000/sysv4.h"
|
||||
tmake_file="rs6000/t-fprules rs6000/t-ppcos t-slibgcc-elf-ver t-linux rs6000/t-ppccomm"
|
||||
case ${enable_targets}:${cpu_is_64bit} in
|
||||
*powerpc64* | all:* | *:yes)
|
||||
if test x$cpu_is_64bit = xyes; then
|
||||
tm_file="${tm_file} rs6000/default64.h"
|
||||
fi
|
||||
tm_file="rs6000/biarch64.h ${tm_file} rs6000/linux64.h"
|
||||
tmake_file="$tmake_file rs6000/t-linux64"
|
||||
;;
|
||||
*)
|
||||
tm_file="${tm_file} rs6000/linux.h"
|
||||
;;
|
||||
esac
|
||||
;;
|
||||
powerpc-*-gnu-gnualtivec*)
|
||||
tm_file="${cpu_type}/${cpu_type}.h elfos.h svr4.h freebsd-spec.h gnu.h rs6000/sysv4.h rs6000/linux.h rs6000/linuxaltivec.h rs6000/gnu.h"
|
||||
@ -2007,7 +2025,7 @@ sparc64-*-openbsd*)
|
||||
with_cpu=ultrasparc
|
||||
;;
|
||||
sparc-*-elf*)
|
||||
tm_file="${tm_file} dbxelf.h elfos.h svr4.h sparc/sysv4.h sol2.h sparc/sol2.h sparc/elf.h"
|
||||
tm_file="${tm_file} dbxelf.h elfos.h svr4.h sparc/sysv4.h sol2.h sparc/sol2.h sparc/sol2-gld.h sparc/elf.h"
|
||||
tmake_file="sparc/t-elf sparc/t-crtfm"
|
||||
extra_parts="crti.o crtn.o crtbegin.o crtend.o"
|
||||
use_fixproto=yes
|
||||
@ -2017,7 +2035,7 @@ sparc-*-linux*) # SPARC's running GNU/Linux, libc6
|
||||
tmake_file="t-slibgcc-elf-ver t-linux sparc/t-crtfm"
|
||||
;;
|
||||
sparc-*-rtems*)
|
||||
tm_file="${tm_file} dbxelf.h elfos.h svr4.h sparc/sysv4.h sol2.h sparc/sol2.h sparc/elf.h sparc/rtemself.h rtems.h"
|
||||
tm_file="${tm_file} dbxelf.h elfos.h svr4.h sparc/sysv4.h sol2.h sparc/sol2.h sparc/sol2-gld.h sparc/elf.h sparc/rtemself.h rtems.h"
|
||||
tmake_file="sparc/t-elf sparc/t-crtfm t-rtems"
|
||||
extra_parts="crti.o crtn.o crtbegin.o crtend.o"
|
||||
;;
|
||||
@ -2106,13 +2124,13 @@ sparclite-*-coff*)
|
||||
tmake_file=sparc/t-sparclite
|
||||
;;
|
||||
sparclite-*-elf*)
|
||||
tm_file="${tm_file} dbxelf.h elfos.h svr4.h sparc/sysv4.h sol2.h sparc/sol2.h sparc/elf.h sparc/liteelf.h"
|
||||
tm_file="${tm_file} dbxelf.h elfos.h svr4.h sparc/sysv4.h sol2.h sparc/sol2.h sparc/sol2-gld.h sparc/elf.h sparc/liteelf.h"
|
||||
tmake_file="sparc/t-sparclite sparc/t-crtfm"
|
||||
extra_parts="crtbegin.o crtend.o"
|
||||
use_fixproto=yes
|
||||
;;
|
||||
sparc86x-*-elf*)
|
||||
tm_file="${tm_file} dbxelf.h elfos.h svr4.h sparc/sysv4.h sol2.h sparc/sol2.h sparc/elf.h sparc/sp86x-elf.h"
|
||||
tm_file="${tm_file} dbxelf.h elfos.h svr4.h sparc/sysv4.h sol2.h sparc/sol2.h sparc/sol2-gld.h sparc/elf.h sparc/sp86x-elf.h"
|
||||
tmake_file="sparc/t-sp86x sparc/t-crtfm"
|
||||
extra_parts="crtbegin.o crtend.o"
|
||||
use_fixproto=yes
|
||||
@ -2122,7 +2140,7 @@ sparc64-*-aout*)
|
||||
use_fixproto=yes
|
||||
;;
|
||||
sparc64-*-elf*)
|
||||
tm_file="${tm_file} dbxelf.h elfos.h svr4.h sparc/sysv4.h sol2.h sparc/sol2.h sparc/sp64-elf.h"
|
||||
tm_file="${tm_file} dbxelf.h elfos.h svr4.h sparc/sysv4.h sol2.h sparc/sol2.h sparc/sol2-gld.h sparc/sp64-elf.h"
|
||||
tmake_file="${tmake_file} sparc/t-crtfm"
|
||||
extra_parts="crtbegin.o crtend.o"
|
||||
use_fixproto=yes
|
||||
@ -2398,24 +2416,24 @@ if test x$with_cpu = x ; then
|
||||
esac
|
||||
fi
|
||||
|
||||
# Similarly for --with-schedule.
|
||||
if test x$with_schedule = x; then
|
||||
case ${target} in
|
||||
hppa1* | parisc1*)
|
||||
# Override default PA8000 scheduling model.
|
||||
with_schedule=7100LC
|
||||
;;
|
||||
esac
|
||||
fi
|
||||
# Similarly for --with-schedule.
|
||||
if test x$with_schedule = x; then
|
||||
case ${target} in
|
||||
hppa1* | parisc1*)
|
||||
# Override default PA8000 scheduling model.
|
||||
with_schedule=7100LC
|
||||
;;
|
||||
esac
|
||||
fi
|
||||
|
||||
# Validate and mark as valid any --with options supported
|
||||
# by this target. In order to use a particular --with option
|
||||
# you must list it in supported_defaults; validating the value
|
||||
# is optional. This case statement should set nothing besides
|
||||
# supported_defaults.
|
||||
# Validate and mark as valid any --with options supported
|
||||
# by this target. In order to use a particular --with option
|
||||
# you must list it in supported_defaults; validating the value
|
||||
# is optional. This case statement should set nothing besides
|
||||
# supported_defaults.
|
||||
|
||||
supported_defaults=
|
||||
case "${target}" in
|
||||
supported_defaults=
|
||||
case "${target}" in
|
||||
alpha*-*-*)
|
||||
supported_defaults="cpu tune"
|
||||
for which in cpu tune; do
|
||||
@ -2569,8 +2587,7 @@ fi
|
||||
eval $with_which=
|
||||
;;
|
||||
"" | common \
|
||||
| power | power2 | power3 | power4 \
|
||||
| powerpc | powerpc64 \
|
||||
| power | power[2345] | powerpc | powerpc64 \
|
||||
| rios | rios1 | rios2 | rsc | rsc1 | rs64a \
|
||||
| 401 | 403 | 405 | 405fp | 440 | 440fp | 505 \
|
||||
| 601 | 602 | 603 | 603e | ec603e | 604 \
|
||||
@ -2655,11 +2672,11 @@ fi
|
||||
;;
|
||||
esac
|
||||
;;
|
||||
esac
|
||||
esac
|
||||
|
||||
# Set some miscellaneous flags for particular targets.
|
||||
target_cpu_default2=
|
||||
case ${target} in
|
||||
# Set some miscellaneous flags for particular targets.
|
||||
target_cpu_default2=
|
||||
case ${target} in
|
||||
alpha*-*-*)
|
||||
if test x$gas = xyes
|
||||
then
|
||||
@ -2771,44 +2788,45 @@ fi
|
||||
;;
|
||||
esac
|
||||
;;
|
||||
esac
|
||||
esac
|
||||
|
||||
t=
|
||||
all_defaults="abi cpu arch tune schedule float mode"
|
||||
for option in $all_defaults
|
||||
do
|
||||
eval "val=\$with_$option"
|
||||
if test -n "$val"; then
|
||||
case " $supported_defaults " in
|
||||
*" $option "*)
|
||||
;;
|
||||
*)
|
||||
echo "This target does not support --with-$option." 2>&1
|
||||
exit 1
|
||||
;;
|
||||
esac
|
||||
t=
|
||||
all_defaults="abi cpu arch tune schedule float mode"
|
||||
for option in $all_defaults
|
||||
do
|
||||
eval "val=\$with_$option"
|
||||
if test -n "$val"; then
|
||||
case " $supported_defaults " in
|
||||
*" $option "*)
|
||||
;;
|
||||
*)
|
||||
echo "This target does not support --with-$option." 2>&1
|
||||
exit 1
|
||||
;;
|
||||
esac
|
||||
|
||||
if test "x$t" = x
|
||||
then
|
||||
t="{ \"$option\", \"$val\" }"
|
||||
else
|
||||
t="${t}, { \"$option\", \"$val\" }"
|
||||
fi
|
||||
fi
|
||||
done
|
||||
if test "x$t" = x
|
||||
then
|
||||
configure_default_options="{ { NULL, NULL} }"
|
||||
else
|
||||
configure_default_options="{ ${t} }"
|
||||
fi
|
||||
|
||||
if test "$target_cpu_default2" != ""
|
||||
then
|
||||
if test "$target_cpu_default" != ""
|
||||
if test "x$t" = x
|
||||
then
|
||||
target_cpu_default="(${target_cpu_default}|${target_cpu_default2})"
|
||||
t="{ \"$option\", \"$val\" }"
|
||||
else
|
||||
target_cpu_default=$target_cpu_default2
|
||||
t="${t}, { \"$option\", \"$val\" }"
|
||||
fi
|
||||
fi
|
||||
done
|
||||
|
||||
if test "x$t" = x
|
||||
then
|
||||
configure_default_options="{ { NULL, NULL} }"
|
||||
else
|
||||
configure_default_options="{ ${t} }"
|
||||
fi
|
||||
|
||||
if test "$target_cpu_default2" != ""
|
||||
then
|
||||
if test "$target_cpu_default" != ""
|
||||
then
|
||||
target_cpu_default="(${target_cpu_default}|${target_cpu_default2})"
|
||||
else
|
||||
target_cpu_default=$target_cpu_default2
|
||||
fi
|
||||
fi
|
||||
|
@ -262,6 +262,9 @@
|
||||
skip when using the GAS .p2align command. */
|
||||
#undef HAVE_GAS_MAX_SKIP_P2ALIGN
|
||||
|
||||
/* Define if your assembler supports .nsubspa comdat option. */
|
||||
#undef HAVE_GAS_NSUBSPA_COMDAT
|
||||
|
||||
/* Define 0/1 if your assembler supports marking sections with SHF_MERGE flag.
|
||||
*/
|
||||
#undef HAVE_GAS_SHF_MERGE
|
||||
@ -319,6 +322,9 @@
|
||||
a read-write section. */
|
||||
#undef HAVE_LD_RO_RW_SECTION_MIXING
|
||||
|
||||
/* Define if your linker supports -Bstatic/-Bdynamic option. */
|
||||
#undef HAVE_LD_STATIC_DYNAMIC
|
||||
|
||||
/* Define to 1 if you have the <limits.h> header file. */
|
||||
#undef HAVE_LIMITS_H
|
||||
|
||||
@ -534,9 +540,6 @@
|
||||
/* Define if your assembler mis-optimizes .eh_frame data. */
|
||||
#undef USE_AS_TRADITIONAL_FORMAT
|
||||
|
||||
/* Define if gcc should use -lunwind. */
|
||||
#undef USE_LIBUNWIND_EXCEPTIONS
|
||||
|
||||
/* Define to be the last portion of registry key on windows hosts. */
|
||||
#undef WIN32_REGISTRY_KEY
|
||||
|
||||
@ -549,9 +552,11 @@
|
||||
/* Define to `int' if <sys/types.h> doesn't define. */
|
||||
#undef gid_t
|
||||
|
||||
/* Define as `__inline' if that's what the C compiler calls it, or to nothing
|
||||
if it is not supported. */
|
||||
/* Define to `__inline__' or `__inline' if that's what the C compiler
|
||||
calls it, or to nothing if 'inline' is not supported under any name. */
|
||||
#ifndef __cplusplus
|
||||
#undef inline
|
||||
#endif
|
||||
|
||||
/* Define to `int' if <sys/types.h> does not define. */
|
||||
#undef pid_t
|
||||
|
@ -1947,6 +1947,17 @@ alpha_legitimize_address (rtx x, rtx scratch,
|
||||
}
|
||||
}
|
||||
|
||||
/* Primarily this is required for TLS symbols, but given that our move
|
||||
patterns *ought* to be able to handle any symbol at any time, we
|
||||
should never be spilling symbolic operands to the constant pool, ever. */
|
||||
|
||||
static bool
|
||||
alpha_cannot_force_const_mem (rtx x)
|
||||
{
|
||||
enum rtx_code code = GET_CODE (x);
|
||||
return code == SYMBOL_REF || code == LABEL_REF || code == CONST;
|
||||
}
|
||||
|
||||
/* We do not allow indirect calls to be optimized into sibling calls, nor
|
||||
can we allow a call to a function with a different GP to be optimized
|
||||
into a sibcall. */
|
||||
@ -3186,7 +3197,13 @@ alpha_emit_conditional_branch (enum rtx_code code)
|
||||
/* If the constants doesn't fit into an immediate, but can
|
||||
be generated by lda/ldah, we adjust the argument and
|
||||
compare against zero, so we can use beq/bne directly. */
|
||||
else if (GET_CODE (op1) == CONST_INT && (code == EQ || code == NE))
|
||||
/* ??? Don't do this when comparing against symbols, otherwise
|
||||
we'll reduce (&x == 0x1234) to (&x-0x1234 == 0), which will
|
||||
be declared false out of hand (at least for non-weak). */
|
||||
else if (GET_CODE (op1) == CONST_INT
|
||||
&& (code == EQ || code == NE)
|
||||
&& !(symbolic_operand (op0, VOIDmode)
|
||||
|| (GET_CODE (op0) == REG && REG_POINTER (op0))))
|
||||
{
|
||||
HOST_WIDE_INT v = INTVAL (op1), n = -v;
|
||||
|
||||
@ -6786,11 +6803,6 @@ alpha_sa_mask (unsigned long *imaskP, unsigned long *fmaskP)
|
||||
break;
|
||||
imask |= 1UL << regno;
|
||||
}
|
||||
|
||||
/* Glibc likes to use $31 as an unwind stopper for crt0. To
|
||||
avoid hackery in unwind-dw2.c, we need to actively store a
|
||||
zero in the prologue of _Unwind_RaiseException et al. */
|
||||
imask |= 1UL << 31;
|
||||
}
|
||||
|
||||
/* If any register spilled, then spill the return address also. */
|
||||
@ -7046,6 +7058,48 @@ set_frame_related_p (void)
|
||||
|
||||
#define FRP(exp) (start_sequence (), exp, set_frame_related_p ())
|
||||
|
||||
/* Generates a store with the proper unwind info attached. VALUE is
|
||||
stored at BASE_REG+BASE_OFS. If FRAME_BIAS is non-zero, then BASE_REG
|
||||
contains SP+FRAME_BIAS, and that is the unwind info that should be
|
||||
generated. If FRAME_REG != VALUE, then VALUE is being stored on
|
||||
behalf of FRAME_REG, and FRAME_REG should be present in the unwind. */
|
||||
|
||||
static void
|
||||
emit_frame_store_1 (rtx value, rtx base_reg, HOST_WIDE_INT frame_bias,
|
||||
HOST_WIDE_INT base_ofs, rtx frame_reg)
|
||||
{
|
||||
rtx addr, mem, insn;
|
||||
|
||||
addr = plus_constant (base_reg, base_ofs);
|
||||
mem = gen_rtx_MEM (DImode, addr);
|
||||
set_mem_alias_set (mem, alpha_sr_alias_set);
|
||||
|
||||
insn = emit_move_insn (mem, value);
|
||||
RTX_FRAME_RELATED_P (insn) = 1;
|
||||
|
||||
if (frame_bias || value != frame_reg)
|
||||
{
|
||||
if (frame_bias)
|
||||
{
|
||||
addr = plus_constant (stack_pointer_rtx, frame_bias + base_ofs);
|
||||
mem = gen_rtx_MEM (DImode, addr);
|
||||
}
|
||||
|
||||
REG_NOTES (insn)
|
||||
= gen_rtx_EXPR_LIST (REG_FRAME_RELATED_EXPR,
|
||||
gen_rtx_SET (VOIDmode, mem, frame_reg),
|
||||
REG_NOTES (insn));
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
emit_frame_store (unsigned int regno, rtx base_reg,
|
||||
HOST_WIDE_INT frame_bias, HOST_WIDE_INT base_ofs)
|
||||
{
|
||||
rtx reg = gen_rtx_REG (DImode, regno);
|
||||
emit_frame_store_1 (reg, base_reg, frame_bias, base_ofs, reg);
|
||||
}
|
||||
|
||||
/* Write function prologue. */
|
||||
|
||||
/* On vms we have two kinds of functions:
|
||||
@ -7075,7 +7129,7 @@ alpha_expand_prologue (void)
|
||||
HOST_WIDE_INT frame_size;
|
||||
/* Offset from base reg to register save area. */
|
||||
HOST_WIDE_INT reg_offset;
|
||||
rtx sa_reg, mem;
|
||||
rtx sa_reg;
|
||||
int i;
|
||||
|
||||
sa_size = alpha_sa_size ();
|
||||
@ -7225,37 +7279,40 @@ alpha_expand_prologue (void)
|
||||
|
||||
if (!TARGET_ABI_UNICOSMK)
|
||||
{
|
||||
HOST_WIDE_INT sa_bias = 0;
|
||||
|
||||
/* Cope with very large offsets to the register save area. */
|
||||
sa_reg = stack_pointer_rtx;
|
||||
if (reg_offset + sa_size > 0x8000)
|
||||
{
|
||||
int low = ((reg_offset & 0xffff) ^ 0x8000) - 0x8000;
|
||||
HOST_WIDE_INT bias;
|
||||
rtx sa_bias_rtx;
|
||||
|
||||
if (low + sa_size <= 0x8000)
|
||||
bias = reg_offset - low, reg_offset = low;
|
||||
sa_bias = reg_offset - low, reg_offset = low;
|
||||
else
|
||||
bias = reg_offset, reg_offset = 0;
|
||||
sa_bias = reg_offset, reg_offset = 0;
|
||||
|
||||
sa_reg = gen_rtx_REG (DImode, 24);
|
||||
FRP (emit_insn (gen_adddi3 (sa_reg, stack_pointer_rtx,
|
||||
GEN_INT (bias))));
|
||||
sa_bias_rtx = GEN_INT (sa_bias);
|
||||
|
||||
if (add_operand (sa_bias_rtx, DImode))
|
||||
emit_insn (gen_adddi3 (sa_reg, stack_pointer_rtx, sa_bias_rtx));
|
||||
else
|
||||
{
|
||||
emit_move_insn (sa_reg, sa_bias_rtx);
|
||||
emit_insn (gen_adddi3 (sa_reg, stack_pointer_rtx, sa_reg));
|
||||
}
|
||||
}
|
||||
|
||||
/* Save regs in stack order. Beginning with VMS PV. */
|
||||
if (TARGET_ABI_OPEN_VMS && alpha_procedure_type == PT_STACK)
|
||||
{
|
||||
mem = gen_rtx_MEM (DImode, stack_pointer_rtx);
|
||||
set_mem_alias_set (mem, alpha_sr_alias_set);
|
||||
FRP (emit_move_insn (mem, gen_rtx_REG (DImode, REG_PV)));
|
||||
}
|
||||
emit_frame_store (REG_PV, stack_pointer_rtx, 0, 0);
|
||||
|
||||
/* Save register RA next. */
|
||||
if (imask & (1UL << REG_RA))
|
||||
{
|
||||
mem = gen_rtx_MEM (DImode, plus_constant (sa_reg, reg_offset));
|
||||
set_mem_alias_set (mem, alpha_sr_alias_set);
|
||||
FRP (emit_move_insn (mem, gen_rtx_REG (DImode, REG_RA)));
|
||||
emit_frame_store (REG_RA, sa_reg, sa_bias, reg_offset);
|
||||
imask &= ~(1UL << REG_RA);
|
||||
reg_offset += 8;
|
||||
}
|
||||
@ -7264,36 +7321,14 @@ alpha_expand_prologue (void)
|
||||
for (i = 0; i < 31; i++)
|
||||
if (imask & (1UL << i))
|
||||
{
|
||||
mem = gen_rtx_MEM (DImode, plus_constant (sa_reg, reg_offset));
|
||||
set_mem_alias_set (mem, alpha_sr_alias_set);
|
||||
FRP (emit_move_insn (mem, gen_rtx_REG (DImode, i)));
|
||||
emit_frame_store (i, sa_reg, sa_bias, reg_offset);
|
||||
reg_offset += 8;
|
||||
}
|
||||
|
||||
/* Store a zero if requested for unwinding. */
|
||||
if (imask & (1UL << 31))
|
||||
{
|
||||
rtx insn, t;
|
||||
|
||||
mem = gen_rtx_MEM (DImode, plus_constant (sa_reg, reg_offset));
|
||||
set_mem_alias_set (mem, alpha_sr_alias_set);
|
||||
insn = emit_move_insn (mem, const0_rtx);
|
||||
|
||||
RTX_FRAME_RELATED_P (insn) = 1;
|
||||
t = gen_rtx_REG (Pmode, 31);
|
||||
t = gen_rtx_SET (VOIDmode, mem, t);
|
||||
t = gen_rtx_EXPR_LIST (REG_FRAME_RELATED_EXPR, t, REG_NOTES (insn));
|
||||
REG_NOTES (insn) = t;
|
||||
|
||||
reg_offset += 8;
|
||||
}
|
||||
|
||||
for (i = 0; i < 31; i++)
|
||||
if (fmask & (1UL << i))
|
||||
{
|
||||
mem = gen_rtx_MEM (DFmode, plus_constant (sa_reg, reg_offset));
|
||||
set_mem_alias_set (mem, alpha_sr_alias_set);
|
||||
FRP (emit_move_insn (mem, gen_rtx_REG (DFmode, i+32)));
|
||||
emit_frame_store (i+32, sa_reg, sa_bias, reg_offset);
|
||||
reg_offset += 8;
|
||||
}
|
||||
}
|
||||
@ -7307,19 +7342,13 @@ alpha_expand_prologue (void)
|
||||
for (i = 9; i < 15; i++)
|
||||
if (imask & (1UL << i))
|
||||
{
|
||||
mem = gen_rtx_MEM (DImode, plus_constant(hard_frame_pointer_rtx,
|
||||
reg_offset));
|
||||
set_mem_alias_set (mem, alpha_sr_alias_set);
|
||||
FRP (emit_move_insn (mem, gen_rtx_REG (DImode, i)));
|
||||
emit_frame_store (i, hard_frame_pointer_rtx, 0, reg_offset);
|
||||
reg_offset -= 8;
|
||||
}
|
||||
for (i = 2; i < 10; i++)
|
||||
if (fmask & (1UL << i))
|
||||
{
|
||||
mem = gen_rtx_MEM (DFmode, plus_constant (hard_frame_pointer_rtx,
|
||||
reg_offset));
|
||||
set_mem_alias_set (mem, alpha_sr_alias_set);
|
||||
FRP (emit_move_insn (mem, gen_rtx_REG (DFmode, i+32)));
|
||||
emit_frame_store (i+32, hard_frame_pointer_rtx, 0, reg_offset);
|
||||
reg_offset -= 8;
|
||||
}
|
||||
}
|
||||
@ -7713,9 +7742,6 @@ alpha_expand_epilogue (void)
|
||||
reg_offset += 8;
|
||||
}
|
||||
|
||||
if (imask & (1UL << 31))
|
||||
reg_offset += 8;
|
||||
|
||||
for (i = 0; i < 31; ++i)
|
||||
if (fmask & (1UL << i))
|
||||
{
|
||||
@ -10215,6 +10241,8 @@ alpha_init_libfuncs (void)
|
||||
#define TARGET_FUNCTION_OK_FOR_SIBCALL alpha_function_ok_for_sibcall
|
||||
#undef TARGET_CANNOT_COPY_INSN_P
|
||||
#define TARGET_CANNOT_COPY_INSN_P alpha_cannot_copy_insn_p
|
||||
#undef TARGET_CANNOT_FORCE_CONST_MEM
|
||||
#define TARGET_CANNOT_FORCE_CONST_MEM alpha_cannot_force_const_mem
|
||||
|
||||
#if TARGET_ABI_OSF
|
||||
#undef TARGET_ASM_OUTPUT_MI_THUNK
|
||||
@ -10257,4 +10285,3 @@ struct gcc_target targetm = TARGET_INITIALIZER;
|
||||
|
||||
|
||||
#include "gt-alpha.h"
|
||||
|
||||
|
@ -641,6 +641,7 @@ extern const char *alpha_tls_size_string; /* For -mtls-size= */
|
||||
#define HARD_REGNO_MODE_OK(REGNO, MODE) \
|
||||
((REGNO) >= 32 && (REGNO) <= 62 \
|
||||
? (MODE) == SFmode || (MODE) == DFmode || (MODE) == DImode \
|
||||
|| (MODE) == SCmode || (MODE) == DCmode \
|
||||
: 1)
|
||||
|
||||
/* Value is 1 if MODE is a supported vector mode. */
|
||||
@ -1189,6 +1190,7 @@ do { \
|
||||
#define INCOMING_RETURN_ADDR_RTX gen_rtx_REG (Pmode, 26)
|
||||
#define DWARF_FRAME_RETURN_COLUMN DWARF_FRAME_REGNUM (26)
|
||||
#define DWARF_ALT_FRAME_RETURN_COLUMN DWARF_FRAME_REGNUM (64)
|
||||
#define DWARF_ZERO_REG 31
|
||||
|
||||
/* Describe how we implement __builtin_eh_return. */
|
||||
#define EH_RETURN_DATA_REGNO(N) ((N) < 4 ? (N) + 16 : INVALID_REGNUM)
|
||||
|
@ -77,6 +77,7 @@
|
||||
(UNSPECV_PLDGP2 11) ; prologue ldgp
|
||||
(UNSPECV_SET_TP 12)
|
||||
(UNSPECV_RPCC 13)
|
||||
(UNSPECV_SETJMPR_ER 14) ; builtin_setjmp_receiver fragment
|
||||
])
|
||||
|
||||
;; Where necessary, the suffixes _le and _be are used to distinguish between
|
||||
@ -438,9 +439,9 @@
|
||||
;; and if we split before reload, we will require additional instructions.
|
||||
|
||||
(define_insn "*adddi_fp_hack"
|
||||
[(set (match_operand:DI 0 "register_operand" "=r")
|
||||
(plus:DI (match_operand:DI 1 "reg_no_subreg_operand" "r")
|
||||
(match_operand:DI 2 "const_int_operand" "n")))]
|
||||
[(set (match_operand:DI 0 "register_operand" "=r,r,r")
|
||||
(plus:DI (match_operand:DI 1 "reg_no_subreg_operand" "r,r,r")
|
||||
(match_operand:DI 2 "const_int_operand" "K,L,n")))]
|
||||
"NONSTRICT_REG_OK_FP_BASE_P (operands[1])
|
||||
&& INTVAL (operands[2]) >= 0
|
||||
/* This is the largest constant an lda+ldah pair can add, minus
|
||||
@ -454,7 +455,10 @@
|
||||
+ max_reg_num () * UNITS_PER_WORD
|
||||
+ current_function_pretend_args_size)
|
||||
- current_function_pretend_args_size))"
|
||||
"#")
|
||||
"@
|
||||
lda %0,%2(%1)
|
||||
ldah %0,%h2(%1)
|
||||
#")
|
||||
|
||||
;; Don't do this if we are adjusting SP since we don't want to do it
|
||||
;; in two steps. Don't split FP sources for the reason listed above.
|
||||
@ -6897,70 +6901,44 @@
|
||||
"jmp $31,(%0),0"
|
||||
[(set_attr "type" "ibr")])
|
||||
|
||||
(define_insn "*builtin_setjmp_receiver_er_sl_1"
|
||||
[(unspec_volatile [(label_ref (match_operand 0 "" ""))] UNSPECV_SETJMPR)]
|
||||
"TARGET_EXPLICIT_RELOCS && TARGET_ABI_OSF && TARGET_AS_CAN_SUBTRACT_LABELS"
|
||||
"lda $27,$LSJ%=-%l0($27)\n$LSJ%=:")
|
||||
|
||||
(define_insn "*builtin_setjmp_receiver_er_1"
|
||||
[(unspec_volatile [(label_ref (match_operand 0 "" ""))] UNSPECV_SETJMPR)]
|
||||
"TARGET_EXPLICIT_RELOCS && TARGET_ABI_OSF"
|
||||
"br $27,$LSJ%=\n$LSJ%=:"
|
||||
[(set_attr "type" "ibr")])
|
||||
|
||||
(define_split
|
||||
[(unspec_volatile [(label_ref (match_operand 0 "" ""))] UNSPECV_SETJMPR)]
|
||||
"TARGET_EXPLICIT_RELOCS && TARGET_ABI_OSF
|
||||
&& prev_nonnote_insn (insn) == operands[0]"
|
||||
[(const_int 0)]
|
||||
"
|
||||
{
|
||||
emit_note (NOTE_INSN_DELETED);
|
||||
DONE;
|
||||
}")
|
||||
|
||||
(define_insn "*builtin_setjmp_receiver_1"
|
||||
(define_expand "builtin_setjmp_receiver"
|
||||
[(unspec_volatile [(label_ref (match_operand 0 "" ""))] UNSPECV_SETJMPR)]
|
||||
"TARGET_ABI_OSF"
|
||||
"br $27,$LSJ%=\n$LSJ%=:\;ldgp $29,0($27)"
|
||||
[(set_attr "length" "12")
|
||||
(set_attr "type" "multi")])
|
||||
"")
|
||||
|
||||
(define_expand "builtin_setjmp_receiver_er"
|
||||
[(unspec_volatile [(label_ref (match_operand 0 "" ""))] UNSPECV_SETJMPR)
|
||||
(define_insn_and_split "*builtin_setjmp_receiver_1"
|
||||
[(unspec_volatile [(match_operand 0 "" "")] UNSPECV_SETJMPR)]
|
||||
"TARGET_ABI_OSF"
|
||||
{
|
||||
if (TARGET_EXPLICIT_RELOCS)
|
||||
return "#";
|
||||
else
|
||||
return "br $27,$LSJ%=\n$LSJ%=:\;ldgp $29,0($27)";
|
||||
}
|
||||
"&& TARGET_EXPLICIT_RELOCS && reload_completed"
|
||||
[(unspec_volatile [(match_dup 0)] UNSPECV_SETJMPR_ER)
|
||||
(set (match_dup 1)
|
||||
(unspec_volatile:DI [(match_dup 2) (match_dup 3)] UNSPECV_LDGP1))
|
||||
(set (match_dup 1)
|
||||
(unspec:DI [(match_dup 1) (match_dup 3)] UNSPEC_LDGP2))]
|
||||
""
|
||||
{
|
||||
operands[1] = pic_offset_table_rtx;
|
||||
operands[2] = gen_rtx_REG (Pmode, 27);
|
||||
operands[3] = GEN_INT (alpha_next_sequence_number++);
|
||||
})
|
||||
}
|
||||
[(set_attr "length" "12")
|
||||
(set_attr "type" "multi")])
|
||||
|
||||
(define_expand "builtin_setjmp_receiver"
|
||||
[(unspec_volatile [(label_ref (match_operand 0 "" ""))] UNSPECV_SETJMPR)]
|
||||
"TARGET_ABI_OSF"
|
||||
{
|
||||
if (TARGET_EXPLICIT_RELOCS)
|
||||
{
|
||||
emit_insn (gen_builtin_setjmp_receiver_er (operands[0]));
|
||||
DONE;
|
||||
}
|
||||
})
|
||||
(define_insn "*builtin_setjmp_receiver_er_sl_1"
|
||||
[(unspec_volatile [(match_operand 0 "" "")] UNSPECV_SETJMPR_ER)]
|
||||
"TARGET_ABI_OSF && TARGET_EXPLICIT_RELOCS && TARGET_AS_CAN_SUBTRACT_LABELS"
|
||||
"lda $27,$LSJ%=-%l0($27)\n$LSJ%=:")
|
||||
|
||||
(define_expand "exception_receiver_er"
|
||||
[(set (match_dup 0)
|
||||
(unspec_volatile:DI [(match_dup 1) (match_dup 2)] UNSPECV_LDGP1))
|
||||
(set (match_dup 0)
|
||||
(unspec:DI [(match_dup 0) (match_dup 2)] UNSPEC_LDGP2))]
|
||||
""
|
||||
{
|
||||
operands[0] = pic_offset_table_rtx;
|
||||
operands[1] = gen_rtx_REG (Pmode, 26);
|
||||
operands[2] = GEN_INT (alpha_next_sequence_number++);
|
||||
})
|
||||
(define_insn "*builtin_setjmp_receiver_er_1"
|
||||
[(unspec_volatile [(match_operand 0 "" "")] UNSPECV_SETJMPR_ER)]
|
||||
"TARGET_ABI_OSF && TARGET_EXPLICIT_RELOCS"
|
||||
"br $27,$LSJ%=\n$LSJ%=:"
|
||||
[(set_attr "type" "ibr")])
|
||||
|
||||
(define_expand "exception_receiver"
|
||||
[(unspec_volatile [(match_dup 0)] UNSPECV_EHR)]
|
||||
@ -6968,28 +6946,38 @@
|
||||
{
|
||||
if (TARGET_LD_BUGGY_LDGP)
|
||||
operands[0] = alpha_gp_save_rtx ();
|
||||
else if (TARGET_EXPLICIT_RELOCS)
|
||||
{
|
||||
emit_insn (gen_exception_receiver_er ());
|
||||
DONE;
|
||||
}
|
||||
else
|
||||
operands[0] = const0_rtx;
|
||||
})
|
||||
|
||||
(define_insn "*exception_receiver_1"
|
||||
[(unspec_volatile [(const_int 0)] UNSPECV_EHR)]
|
||||
"! TARGET_LD_BUGGY_LDGP"
|
||||
"ldgp $29,0($26)"
|
||||
[(set_attr "length" "8")
|
||||
(set_attr "type" "multi")])
|
||||
|
||||
(define_insn "*exception_receiver_2"
|
||||
[(unspec_volatile [(match_operand:DI 0 "memory_operand" "m")] UNSPECV_EHR)]
|
||||
"TARGET_LD_BUGGY_LDGP"
|
||||
"TARGET_ABI_OSF && TARGET_LD_BUGGY_LDGP"
|
||||
"ldq $29,%0"
|
||||
[(set_attr "type" "ild")])
|
||||
|
||||
(define_insn_and_split "*exception_receiver_1"
|
||||
[(unspec_volatile [(const_int 0)] UNSPECV_EHR)]
|
||||
"TARGET_ABI_OSF"
|
||||
{
|
||||
if (TARGET_EXPLICIT_RELOCS)
|
||||
return "ldah $29,0($26)\t\t!gpdisp!%*\;lda $29,0($29)\t\t!gpdisp!%*";
|
||||
else
|
||||
return "ldgp $29,0($26)";
|
||||
}
|
||||
"&& TARGET_EXPLICIT_RELOCS && reload_completed"
|
||||
[(set (match_dup 0)
|
||||
(unspec_volatile:DI [(match_dup 1) (match_dup 2)] UNSPECV_LDGP1))
|
||||
(set (match_dup 0)
|
||||
(unspec:DI [(match_dup 0) (match_dup 2)] UNSPEC_LDGP2))]
|
||||
{
|
||||
operands[0] = pic_offset_table_rtx;
|
||||
operands[1] = gen_rtx_REG (Pmode, 26);
|
||||
operands[2] = GEN_INT (alpha_next_sequence_number++);
|
||||
}
|
||||
[(set_attr "length" "8")
|
||||
(set_attr "type" "multi")])
|
||||
|
||||
(define_expand "nonlocal_goto_receiver"
|
||||
[(unspec_volatile [(const_int 0)] UNSPECV_BLOCKAGE)
|
||||
(set (reg:DI 27) (mem:DI (reg:DI 29)))
|
||||
|
@ -26,6 +26,10 @@
|
||||
# Free Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
|
||||
# MA 02111-1307, USA.
|
||||
|
||||
#ifdef __ELF__
|
||||
.section .note.GNU-stack,""
|
||||
#endif
|
||||
|
||||
.set noreorder
|
||||
.set noat
|
||||
|
||||
|
@ -16,8 +16,12 @@ SHLIB_LINK = $(GCC_FOR_TARGET) $(LIBGCC2_CFLAGS) -shared -nodefaultlibs \
|
||||
-Wl,-hidden_symbol,pthread\* -Wl,-hidden_symbol,__pthread\* \
|
||||
-Wl,-hidden_symbol,sched_get_\* -Wl,-hidden_symbol,sched_yield \
|
||||
-Wl,-msym -Wl,-set_version,gcc.1 -Wl,-soname,$(SHLIB_SONAME) \
|
||||
-o $(SHLIB_NAME) @multilib_flags@ $(SHLIB_OBJS) -lc && \
|
||||
-o $(SHLIB_NAME).tmp @multilib_flags@ $(SHLIB_OBJS) -lc && \
|
||||
rm -f $(SHLIB_SONAME) && \
|
||||
if [ -f $(SHLIB_NAME) ]; then \
|
||||
mv -f $(SHLIB_NAME) $(SHLIB_NAME).backup; \
|
||||
else true; fi && \
|
||||
mv $(SHLIB_NAME).tmp $(SHLIB_NAME) && \
|
||||
$(LN_S) $(SHLIB_NAME) $(SHLIB_SONAME)
|
||||
# $(slibdir) double quoted to protect it from expansion while building
|
||||
# libgcc.mk. We want this delayed until actual install time.
|
||||
|
@ -1,5 +1,6 @@
|
||||
/* Prototypes for exported functions defined in arm.c and pe.c
|
||||
Copyright (C) 1999, 2000, 2001, 2002, 2003 Free Software Foundation, Inc.
|
||||
Copyright (C) 1999, 2000, 2001, 2002, 2003, 2005
|
||||
Free Software Foundation, Inc.
|
||||
Contributed by Richard Earnshaw (rearnsha@arm.com)
|
||||
Minor hacks by Nick Clifton (nickc@cygnus.com)
|
||||
|
||||
@ -138,6 +139,7 @@ extern int arm_debugger_arg_offset (int, rtx);
|
||||
extern int arm_is_longcall_p (rtx, int, int);
|
||||
extern int arm_emit_vector_const (FILE *, rtx);
|
||||
extern const char * arm_output_load_gr (rtx *);
|
||||
extern int arm_eliminable_register (rtx);
|
||||
|
||||
#if defined TREE_CODE
|
||||
extern rtx arm_function_arg (CUMULATIVE_ARGS *, enum machine_mode, tree, int);
|
||||
|
@ -1,6 +1,6 @@
|
||||
/* Output routines for GCC for ARM.
|
||||
Copyright (C) 1991, 1993, 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001,
|
||||
2002, 2003, 2004 Free Software Foundation, Inc.
|
||||
2002, 2003, 2004, 2005 Free Software Foundation, Inc.
|
||||
Contributed by Pieter `Tiggr' Schoenmakers (rcpieter@win.tue.nl)
|
||||
and Martin Simmons (@harleqn.co.uk).
|
||||
More major hacks by Richard Earnshaw (rearnsha@arm.com).
|
||||
@ -4056,6 +4056,16 @@ cirrus_shift_const (rtx op, enum machine_mode mode ATTRIBUTE_UNUSED)
|
||||
&& INTVAL (op) < 64);
|
||||
}
|
||||
|
||||
/* Return true if X is a register that will be eliminated later on. */
|
||||
int
|
||||
arm_eliminable_register (rtx x)
|
||||
{
|
||||
return REG_P (x) && (REGNO (x) == FRAME_POINTER_REGNUM
|
||||
|| REGNO (x) == ARG_POINTER_REGNUM
|
||||
|| (REGNO (x) >= FIRST_VIRTUAL_REGISTER
|
||||
&& REGNO (x) <= LAST_VIRTUAL_REGISTER));
|
||||
}
|
||||
|
||||
/* Returns TRUE if INSN is an "LDR REG, ADDR" instruction.
|
||||
Use by the Cirrus Maverick code which has to workaround
|
||||
a hardware bug triggered by such instructions. */
|
||||
@ -4569,33 +4579,42 @@ adjacent_mem_locations (rtx a, rtx b)
|
||||
|| (GET_CODE (XEXP (b, 0)) == PLUS
|
||||
&& GET_CODE (XEXP (XEXP (b, 0), 1)) == CONST_INT)))
|
||||
{
|
||||
int val0 = 0, val1 = 0;
|
||||
int reg0, reg1;
|
||||
|
||||
HOST_WIDE_INT val0 = 0, val1 = 0;
|
||||
rtx reg0, reg1;
|
||||
int val_diff;
|
||||
|
||||
if (GET_CODE (XEXP (a, 0)) == PLUS)
|
||||
{
|
||||
reg0 = REGNO (XEXP (XEXP (a, 0), 0));
|
||||
reg0 = XEXP (XEXP (a, 0), 0);
|
||||
val0 = INTVAL (XEXP (XEXP (a, 0), 1));
|
||||
}
|
||||
else
|
||||
reg0 = REGNO (XEXP (a, 0));
|
||||
reg0 = XEXP (a, 0);
|
||||
|
||||
if (GET_CODE (XEXP (b, 0)) == PLUS)
|
||||
{
|
||||
reg1 = REGNO (XEXP (XEXP (b, 0), 0));
|
||||
reg1 = XEXP (XEXP (b, 0), 0);
|
||||
val1 = INTVAL (XEXP (XEXP (b, 0), 1));
|
||||
}
|
||||
else
|
||||
reg1 = REGNO (XEXP (b, 0));
|
||||
reg1 = XEXP (b, 0);
|
||||
|
||||
/* Don't accept any offset that will require multiple
|
||||
instructions to handle, since this would cause the
|
||||
arith_adjacentmem pattern to output an overlong sequence. */
|
||||
if (!const_ok_for_op (PLUS, val0) || !const_ok_for_op (PLUS, val1))
|
||||
return 0;
|
||||
|
||||
return (reg0 == reg1) && ((val1 - val0) == 4 || (val0 - val1) == 4);
|
||||
|
||||
/* Don't allow an eliminable register: register elimination can make
|
||||
the offset too large. */
|
||||
if (arm_eliminable_register (reg0))
|
||||
return 0;
|
||||
|
||||
val_diff = val1 - val0;
|
||||
return ((REGNO (reg0) == REGNO (reg1))
|
||||
&& (val_diff == 4 || val_diff == -4));
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
@ -7301,7 +7320,6 @@ output_call_mem (rtx *operands)
|
||||
return "";
|
||||
}
|
||||
|
||||
|
||||
/* Output a move from arm registers to an fpa registers.
|
||||
OPERANDS[0] is an fpa register.
|
||||
OPERANDS[1] is the first registers of an arm register pair. */
|
||||
|
@ -1396,7 +1396,7 @@ enum reg_class
|
||||
: NO_REGS)
|
||||
|
||||
#define THUMB_SECONDARY_OUTPUT_RELOAD_CLASS(CLASS, MODE, X) \
|
||||
((CLASS) != LO_REGS \
|
||||
((CLASS) != LO_REGS && (CLASS) != BASE_REGS \
|
||||
? ((true_regnum (X) == -1 ? LO_REGS \
|
||||
: (true_regnum (X) + HARD_REGNO_NREGS (0, MODE) > 8) ? LO_REGS \
|
||||
: NO_REGS)) \
|
||||
|
@ -5960,22 +5960,24 @@
|
||||
[(set (pc)
|
||||
(if_then_else
|
||||
(match_operator 5 "equality_operator"
|
||||
[(and:SI (not:SI (match_operand:SI 3 "s_register_operand" "l,l,l,l"))
|
||||
(match_operand:SI 2 "s_register_operand" "0,1,1,1"))
|
||||
[(and:SI (not:SI (match_operand:SI 3 "s_register_operand" "l,l,l,l,l"))
|
||||
(match_operand:SI 2 "s_register_operand" "0,1,1,1,1"))
|
||||
(const_int 0)])
|
||||
(label_ref (match_operand 4 "" ""))
|
||||
(pc)))
|
||||
(set (match_operand:SI 0 "thumb_cbrch_target_operand" "=l,*?h,*?m,*?m")
|
||||
(set (match_operand:SI 0 "thumb_cbrch_target_operand" "=!l,l,*?h,*?m,*?m")
|
||||
(and:SI (not:SI (match_dup 3)) (match_dup 2)))
|
||||
(clobber (match_scratch:SI 1 "=X,l,&l,&l"))]
|
||||
(clobber (match_scratch:SI 1 "=X,l,l,&l,&l"))]
|
||||
"TARGET_THUMB"
|
||||
"*
|
||||
{
|
||||
if (which_alternative == 0)
|
||||
output_asm_insn (\"bic\\t%0, %3\", operands);
|
||||
else if (which_alternative == 1)
|
||||
else if (which_alternative <= 2)
|
||||
{
|
||||
output_asm_insn (\"bic\\t%1, %3\", operands);
|
||||
/* It's ok if OP0 is a lo-reg, even though the mov will set the
|
||||
conditions again, since we're only testing for equality. */
|
||||
output_asm_insn (\"mov\\t%0, %1\", operands);
|
||||
}
|
||||
else
|
||||
@ -6234,10 +6236,10 @@
|
||||
case 1:
|
||||
output_asm_insn (\"cmn\t%1, %2\", operands);
|
||||
break;
|
||||
case 3:
|
||||
case 2:
|
||||
output_asm_insn (\"add\t%0, %1, %2\", operands);
|
||||
break;
|
||||
case 4:
|
||||
case 3:
|
||||
output_asm_insn (\"add\t%0, %0, %2\", operands);
|
||||
break;
|
||||
}
|
||||
@ -7128,8 +7130,8 @@
|
||||
(const_string "no")))
|
||||
(set (attr "length")
|
||||
(if_then_else
|
||||
(and (ge (minus (match_dup 0) (pc)) (const_int -2048))
|
||||
(le (minus (match_dup 0) (pc)) (const_int 2044)))
|
||||
(and (ge (minus (match_dup 0) (pc)) (const_int -2044))
|
||||
(le (minus (match_dup 0) (pc)) (const_int 2048)))
|
||||
(const_int 2)
|
||||
(const_int 4)))]
|
||||
)
|
||||
|
@ -11,8 +11,12 @@ SHLIB_OBJS = @shlib_objs@
|
||||
|
||||
SHLIB_LINK = $(GCC_FOR_TARGET) $(LIBGCC2_CFLAGS) -shared -nodefaultlibs \
|
||||
-Wl,-soname,$(SHLIB_SONAME) \
|
||||
-o $(SHLIB_NAME) @multilib_flags@ $(SHLIB_OBJS) -lc && \
|
||||
-o $(SHLIB_NAME).tmp @multilib_flags@ $(SHLIB_OBJS) -lc && \
|
||||
rm -f $(SHLIB_SONAME) && \
|
||||
if [ -f $(SHLIB_NAME) ]; then \
|
||||
mv -f $(SHLIB_NAME) $(SHLIB_NAME).backup; \
|
||||
else true; fi && \
|
||||
mv $(SHLIB_NAME).tmp $(SHLIB_NAME) && \
|
||||
$(LN_S) $(SHLIB_NAME) $(SHLIB_SONAME)
|
||||
# $(slibdir) double quoted to protect it from expansion while building
|
||||
# libgcc.mk. We want this delayed until actual install time.
|
||||
|
10
contrib/gcc/config/arm/t-rtems
Normal file
10
contrib/gcc/config/arm/t-rtems
Normal file
@ -0,0 +1,10 @@
|
||||
# Custom rtems multilibs
|
||||
|
||||
MULTILIB_OPTIONS = marm/mthumb
|
||||
MULTILIB_DIRNAMES = arm thumb
|
||||
MULTILIB_EXCEPTIONS =
|
||||
MULTILIB_MATCHES = marm=mno-thumb
|
||||
|
||||
MULTILIB_OPTIONS += msoft-float/mhard-float
|
||||
MULTILIB_DIRNAMES += soft fpu
|
||||
MULTILIB_EXCEPTIONS += *mthumb/*mhard-float*
|
@ -65,8 +65,6 @@ extern const char *darwin_strip_name_encoding (const char *);
|
||||
|
||||
extern void machopic_finish (FILE *);
|
||||
|
||||
extern void machopic_output_possible_stub_label (FILE *, const char*);
|
||||
|
||||
extern void darwin_exception_section (void);
|
||||
extern void darwin_eh_frame_section (void);
|
||||
extern void machopic_select_section (tree, int, unsigned HOST_WIDE_INT);
|
||||
|
@ -900,10 +900,6 @@ machopic_finish (FILE *asm_out_file)
|
||||
if (! TREE_USED (temp))
|
||||
continue;
|
||||
|
||||
/* If the symbol is actually defined, we don't need a stub. */
|
||||
if (sym_name[0] == '!' && sym_name[1] == 'T')
|
||||
continue;
|
||||
|
||||
sym_name = darwin_strip_name_encoding (sym_name);
|
||||
|
||||
sym = alloca (strlen (sym_name) + 2);
|
||||
@ -1096,37 +1092,6 @@ update_non_lazy_ptrs (const char *name)
|
||||
}
|
||||
}
|
||||
|
||||
/* Function NAME is being defined, and its label has just been output.
|
||||
If there's already a reference to a stub for this function, we can
|
||||
just emit the stub label now and we don't bother emitting the stub later. */
|
||||
|
||||
void
|
||||
machopic_output_possible_stub_label (FILE *file, const char *name)
|
||||
{
|
||||
tree temp;
|
||||
|
||||
/* Ensure we're looking at a section-encoded name. */
|
||||
if (name[0] != '!' || (name[1] != 't' && name[1] != 'T'))
|
||||
return;
|
||||
|
||||
for (temp = machopic_stubs;
|
||||
temp != NULL_TREE;
|
||||
temp = TREE_CHAIN (temp))
|
||||
{
|
||||
const char *sym_name;
|
||||
|
||||
sym_name = IDENTIFIER_POINTER (TREE_VALUE (temp));
|
||||
if (sym_name[0] == '!' && (sym_name[1] == 'T' || sym_name[1] == 't')
|
||||
&& ! strcmp (name+2, sym_name+2))
|
||||
{
|
||||
ASM_OUTPUT_LABEL (file, IDENTIFIER_POINTER (TREE_PURPOSE (temp)));
|
||||
/* Avoid generating a stub for this. */
|
||||
TREE_USED (temp) = 0;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/* Scan the list of stubs and update any recorded names whose
|
||||
stripped name matches the argument. */
|
||||
|
||||
|
@ -99,7 +99,13 @@ Boston, MA 02111-1307, USA. */
|
||||
Note that an option name with a prefix that matches another option
|
||||
name, that also takes an argument, needs to be modified so the
|
||||
prefix is different, otherwise a '*' after the shorter option will
|
||||
match with the longer one. */
|
||||
match with the longer one.
|
||||
|
||||
The SUBTARGET_OPTION_TRANSLATE_TABLE macro, which _must_ be defined
|
||||
in gcc/config/{i386,rs6000}/darwin.h, should contain any additional
|
||||
command-line option translations specific to the particular target
|
||||
architecture. */
|
||||
|
||||
#define TARGET_OPTION_TRANSLATE_TABLE \
|
||||
{ "-all_load", "-Zall_load" }, \
|
||||
{ "-allowable_client", "-Zallowable_client" }, \
|
||||
@ -126,7 +132,8 @@ Boston, MA 02111-1307, USA. */
|
||||
{ "-multi_module", "-Zmulti_module" }, \
|
||||
{ "-static", "-static -Wa,-static" }, \
|
||||
{ "-single_module", "-Zsingle_module" }, \
|
||||
{ "-unexported_symbols_list", "-Zunexported_symbols_list" }
|
||||
{ "-unexported_symbols_list", "-Zunexported_symbols_list" }, \
|
||||
SUBTARGET_OPTION_TRANSLATE_TABLE
|
||||
|
||||
/* These compiler options take n arguments. */
|
||||
|
||||
@ -390,9 +397,6 @@ do { text_section (); \
|
||||
|| DECL_INITIAL (DECL)) \
|
||||
(* targetm.encode_section_info) (DECL, DECL_RTL (DECL), false); \
|
||||
ASM_OUTPUT_LABEL (FILE, xname); \
|
||||
/* Avoid generating stubs for functions we've just defined by \
|
||||
outputting any required stub name label now. */ \
|
||||
machopic_output_possible_stub_label (FILE, xname); \
|
||||
} while (0)
|
||||
|
||||
#define ASM_DECLARE_CONSTANT_NAME(FILE, NAME, EXP, SIZE) \
|
||||
|
@ -107,12 +107,12 @@ Boston, MA 02111-1307, USA. */
|
||||
500016, select the appropriate libc, depending on whether we're
|
||||
doing profiling or need threads support. At __FreeBSD_version
|
||||
500016 and later, when threads support is requested include both
|
||||
-lc and -lc_r instead of only -lc_r. To make matters interesting,
|
||||
we can't actually use __FreeBSD_version provided by <osreldate.h>
|
||||
directly since it breaks cross-compiling. As a final twist, make
|
||||
it a hard error if -pthread is provided on the command line and gcc
|
||||
was configured with --disable-threads (this will help avoid bug
|
||||
reports from users complaining about threading when they
|
||||
-lc and the threading lib instead of only -lc_r. To make matters
|
||||
interesting, we can't actually use __FreeBSD_version provided by
|
||||
<osreldate.h> directly since it breaks cross-compiling. As a final
|
||||
twist, make it a hard error if -pthread is provided on the command
|
||||
line and gcc was configured with --disable-threads (this will help
|
||||
avoid bug reports from users complaining about threading when they
|
||||
misconfigured the gcc bootstrap but are later consulting FreeBSD
|
||||
manual pages that refer to the mythical -pthread option). */
|
||||
|
||||
@ -129,13 +129,7 @@ is built with the --enable-threads configure-time option.} \
|
||||
%{pg: -lc_p} \
|
||||
}"
|
||||
#else
|
||||
#if FBSD_MAJOR >= 5
|
||||
#define FBSD_LIB_SPEC " \
|
||||
%{!shared: \
|
||||
%{!pg: %{pthread:-lc_r} -lc} \
|
||||
%{pg: %{pthread:-lc_r_p} -lc_p} \
|
||||
}"
|
||||
#else
|
||||
#if FBSD_MAJOR < 5
|
||||
#define FBSD_LIB_SPEC " \
|
||||
%{!shared: \
|
||||
%{!pg: \
|
||||
@ -145,6 +139,12 @@ is built with the --enable-threads configure-time option.} \
|
||||
%{!pthread:-lc_p} \
|
||||
%{pthread:-lc_r_p}} \
|
||||
}"
|
||||
#else
|
||||
#define FBSD_LIB_SPEC " \
|
||||
%{!shared: \
|
||||
%{!pg: %{pthread:-lpthread} -lc} \
|
||||
%{pg: %{pthread:-lpthread_p} -lc_p} \
|
||||
}"
|
||||
#endif
|
||||
#endif
|
||||
|
||||
|
@ -30,13 +30,13 @@ mingw_scan (int argc ATTRIBUTE_UNUSED,
|
||||
const char *const *argv,
|
||||
char **spec_machine)
|
||||
{
|
||||
putenv ("GCC_CYGWIN_MINGW=0");
|
||||
putenv (xstrdup ("GCC_CYGWIN_MINGW=0"));
|
||||
|
||||
while (*++argv)
|
||||
if (strcmp (*argv, "-mno-win32") == 0)
|
||||
putenv ("GCC_CYGWIN_WIN32=0");
|
||||
putenv (xstrdup ("GCC_CYGWIN_WIN32=0"));
|
||||
else if (strcmp (*argv, "-mwin32") == 0)
|
||||
putenv ("GCC_CYGWIN_WIN32=1");
|
||||
putenv (xstrdup ("GCC_CYGWIN_WIN32=1"));
|
||||
else if (strcmp (*argv, "-mno-cygwin") == 0)
|
||||
{
|
||||
char *p = strstr (*spec_machine, "-cygwin");
|
||||
@ -48,7 +48,7 @@ mingw_scan (int argc ATTRIBUTE_UNUSED,
|
||||
strcpy (s + len, "-mingw32");
|
||||
*spec_machine = s;
|
||||
}
|
||||
putenv ("GCC_CYGWIN_MINGW=1");
|
||||
putenv (xstrdup ("GCC_CYGWIN_MINGW=1"));
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
@ -41,6 +41,10 @@ Boston, MA 02111-1307, USA. */
|
||||
#undef CC1_SPEC
|
||||
#define CC1_SPEC "%{!static:-fPIC}"
|
||||
|
||||
/* Use the following macro for any Darwin/x86-specific command-line option
|
||||
translation. */
|
||||
#define SUBTARGET_OPTION_TRANSLATE_TABLE
|
||||
|
||||
#define ASM_SPEC "-arch i386 \
|
||||
%{Zforce_cpusubtype_ALL:-force_cpusubtype_ALL} \
|
||||
%{!Zforce_cpusubtype_ALL:%{mmmx:-force_cpusubtype_ALL}\
|
||||
|
@ -34,7 +34,7 @@
|
||||
#include <xmmintrin.h>
|
||||
|
||||
/* SSE2 */
|
||||
typedef int __v2df __attribute__ ((mode (V2DF)));
|
||||
typedef double __v2df __attribute__ ((mode (V2DF)));
|
||||
typedef int __v2di __attribute__ ((mode (V2DI)));
|
||||
typedef int __v4si __attribute__ ((mode (V4SI)));
|
||||
typedef int __v8hi __attribute__ ((mode (V8HI)));
|
||||
|
@ -138,12 +138,5 @@ Boston, MA 02111-1307, USA. */
|
||||
|
||||
/* FreeBSD sets the rounding precision of the FPU to 53 bits. Let the
|
||||
compiler get the contents of <float.h> and std::numeric_limits correct. */
|
||||
#define SUBTARGET_OVERRIDE_OPTIONS \
|
||||
do { \
|
||||
if (!TARGET_64BIT) { \
|
||||
REAL_MODE_FORMAT (XFmode) \
|
||||
= &ieee_extended_intel_96_round_53_format; \
|
||||
REAL_MODE_FORMAT (TFmode) \
|
||||
= &ieee_extended_intel_96_round_53_format; \
|
||||
} \
|
||||
} while (0)
|
||||
#undef TARGET_96_ROUND_53_LONG_DOUBLE
|
||||
#define TARGET_96_ROUND_53_LONG_DOUBLE (!TARGET_64BIT)
|
||||
|
@ -31,11 +31,13 @@ Software Foundation, 59 Temple Place - Suite 330, Boston, MA
|
||||
the executable file might be covered by the GNU General Public License. */
|
||||
|
||||
|
||||
#include <windows.h>
|
||||
#ifndef __GTHREAD_HIDE_WIN32API
|
||||
# define __GTHREAD_HIDE_WIN32API 1
|
||||
#endif
|
||||
#undef __GTHREAD_I486_INLINE_LOCK_PRIMITIVES
|
||||
#define __GTHREAD_I486_INLINE_LOCK_PRIMITIVES
|
||||
#include <gthr-win32.h>
|
||||
#include <windows.h>
|
||||
|
||||
/* Windows32 threads specific definitions. The windows32 threading model
|
||||
does not map well into pthread-inspired gcc's threading model, and so
|
||||
@ -61,10 +63,9 @@ Software Foundation, 59 Temple Place - Suite 330, Boston, MA
|
||||
This may cause incorrect error return due to truncation values on
|
||||
hw where sizeof (DWORD) > sizeof (int).
|
||||
|
||||
3. We might consider using Critical Sections instead of Windows32
|
||||
mutexes for better performance, but emulating __gthread_mutex_trylock
|
||||
interface becomes more complicated (Win9x does not support
|
||||
TryEnterCriticalSectioni, while NT does).
|
||||
3. We are currently using a special mutex instead of the Critical
|
||||
Sections, since Win9x does not support TryEnterCriticalSection
|
||||
(while NT does).
|
||||
|
||||
The basic framework should work well enough. In the long term, GCC
|
||||
needs to use Structured Exception Handling on Windows32. */
|
||||
@ -145,23 +146,29 @@ __gthr_win32_setspecific (__gthread_key_t key, const void *ptr)
|
||||
void
|
||||
__gthr_win32_mutex_init_function (__gthread_mutex_t *mutex)
|
||||
{
|
||||
/* Create unnamed mutex with default security attr and no initial owner. */
|
||||
*mutex = CreateMutex (NULL, 0, NULL);
|
||||
mutex->counter = -1;
|
||||
mutex->sema = CreateSemaphore (NULL, 0, 65535, NULL);
|
||||
}
|
||||
|
||||
int
|
||||
__gthr_win32_mutex_lock (__gthread_mutex_t *mutex)
|
||||
{
|
||||
if (WaitForSingleObject (*mutex, INFINITE) == WAIT_OBJECT_0)
|
||||
if (InterlockedIncrement (&mutex->counter) == 0 ||
|
||||
WaitForSingleObject (mutex->sema, INFINITE) == WAIT_OBJECT_0)
|
||||
return 0;
|
||||
else
|
||||
return 1;
|
||||
{
|
||||
/* WaitForSingleObject returns WAIT_FAILED, and we can only do
|
||||
some best-effort cleanup here. */
|
||||
InterlockedDecrement (&mutex->counter);
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
|
||||
int
|
||||
__gthr_win32_mutex_trylock (__gthread_mutex_t *mutex)
|
||||
{
|
||||
if (WaitForSingleObject (*mutex, 0) == WAIT_OBJECT_0)
|
||||
if (__GTHR_W32_InterlockedCompareExchange (&mutex->counter, 0, -1) < 0)
|
||||
return 0;
|
||||
else
|
||||
return 1;
|
||||
@ -170,5 +177,8 @@ __gthr_win32_mutex_trylock (__gthread_mutex_t *mutex)
|
||||
int
|
||||
__gthr_win32_mutex_unlock (__gthread_mutex_t *mutex)
|
||||
{
|
||||
return (ReleaseMutex (*mutex) != 0) ? 0 : 1;
|
||||
if (InterlockedDecrement (&mutex->counter) >= 0)
|
||||
return ReleaseSemaphore (mutex->sema, 1, NULL) ? 0 : 1;
|
||||
else
|
||||
return 0;
|
||||
}
|
||||
|
@ -29,6 +29,8 @@ Boston, MA 02111-1307, USA. */
|
||||
FLOAT_MODE (XF, 12, ieee_extended_intel_96_format);
|
||||
ADJUST_FLOAT_FORMAT (XF, (TARGET_128BIT_LONG_DOUBLE
|
||||
? &ieee_extended_intel_128_format
|
||||
: TARGET_96_ROUND_53_LONG_DOUBLE
|
||||
? &ieee_extended_intel_96_round_53_format
|
||||
: &ieee_extended_intel_96_format));
|
||||
ADJUST_BYTESIZE (XF, TARGET_128BIT_LONG_DOUBLE ? 16 : 12);
|
||||
ADJUST_ALIGNMENT (XF, TARGET_128BIT_LONG_DOUBLE ? 16 : 4);
|
||||
|
@ -93,6 +93,7 @@ extern int memory_displacement_operand (rtx, enum machine_mode);
|
||||
extern int cmpsi_operand (rtx, enum machine_mode);
|
||||
extern int long_memory_operand (rtx, enum machine_mode);
|
||||
extern int aligned_operand (rtx, enum machine_mode);
|
||||
extern int compare_operator (rtx, enum machine_mode);
|
||||
extern enum machine_mode ix86_cc_mode (enum rtx_code, rtx, rtx);
|
||||
|
||||
extern int ix86_expand_movstr (rtx, rtx, rtx, rtx);
|
||||
|
@ -522,7 +522,14 @@ const int x86_sse_typeless_stores = m_ATHLON_K8;
|
||||
const int x86_sse_load0_by_pxor = m_PPRO | m_PENT4;
|
||||
const int x86_use_ffreep = m_ATHLON_K8;
|
||||
const int x86_rep_movl_optimal = m_386 | m_PENT | m_PPRO | m_K6;
|
||||
const int x86_inter_unit_moves = ~(m_ATHLON_K8);
|
||||
|
||||
/* ??? HACK! The following is a lie. SSE can hold e.g. SImode, and
|
||||
indeed *must* be able to hold SImode so that SSE2 shifts are able
|
||||
to work right. But this can result in some mighty surprising
|
||||
register allocation when building kernels. Turning this off should
|
||||
make us less likely to all-of-the-sudden select an SSE register. */
|
||||
const int x86_inter_unit_moves = 0; /* ~(m_ATHLON_K8) */
|
||||
|
||||
const int x86_ext_80387_constants = m_K6 | m_ATHLON | m_PENT4 | m_PPRO;
|
||||
|
||||
/* In case the average insn count for single function invocation is
|
||||
@ -2536,6 +2543,34 @@ function_arg_advance (CUMULATIVE_ARGS *cum, /* current arg information */
|
||||
return;
|
||||
}
|
||||
|
||||
/* A subroutine of function_arg. We want to pass a parameter whose nominal
|
||||
type is MODE in REGNO. We try to minimize ABI variation, so MODE may not
|
||||
actually be valid for REGNO with the current ISA. In this case, ALT_MODE
|
||||
is used instead. It must be the same size as MODE, and must be known to
|
||||
be valid for REGNO. Finally, ORIG_MODE is the original mode of the
|
||||
parameter, as seen by the type system. This may be different from MODE
|
||||
when we're mucking with things minimizing ABI variations.
|
||||
|
||||
Returns a REG or a PARALLEL as appropriate. */
|
||||
|
||||
static rtx
|
||||
gen_reg_or_parallel (enum machine_mode mode, enum machine_mode alt_mode,
|
||||
enum machine_mode orig_mode, unsigned int regno)
|
||||
{
|
||||
rtx tmp;
|
||||
|
||||
if (HARD_REGNO_MODE_OK (regno, mode))
|
||||
tmp = gen_rtx_REG (mode, regno);
|
||||
else
|
||||
{
|
||||
tmp = gen_rtx_REG (alt_mode, regno);
|
||||
tmp = gen_rtx_EXPR_LIST (VOIDmode, tmp, const0_rtx);
|
||||
tmp = gen_rtx_PARALLEL (orig_mode, gen_rtvec (1, tmp));
|
||||
}
|
||||
|
||||
return tmp;
|
||||
}
|
||||
|
||||
/* Define where to put the arguments to a function.
|
||||
Value is zero to push the argument on the stack,
|
||||
or a hard register in which to store the argument.
|
||||
@ -2550,12 +2585,11 @@ function_arg_advance (CUMULATIVE_ARGS *cum, /* current arg information */
|
||||
(otherwise it is an extra parameter matching an ellipsis). */
|
||||
|
||||
rtx
|
||||
function_arg (CUMULATIVE_ARGS *cum, /* current arg information */
|
||||
enum machine_mode mode, /* current arg mode */
|
||||
tree type, /* type of the argument or 0 if lib support */
|
||||
int named) /* != 0 for normal args, == 0 for ... args */
|
||||
function_arg (CUMULATIVE_ARGS *cum, enum machine_mode orig_mode,
|
||||
tree type, int named)
|
||||
{
|
||||
rtx ret = NULL_RTX;
|
||||
enum machine_mode mode = orig_mode;
|
||||
rtx ret = NULL_RTX;
|
||||
int bytes =
|
||||
(mode == BLKmode) ? int_size_in_bytes (type) : (int) GET_MODE_SIZE (mode);
|
||||
int words = (bytes + UNITS_PER_WORD - 1) / UNITS_PER_WORD;
|
||||
@ -2628,7 +2662,8 @@ function_arg (CUMULATIVE_ARGS *cum, /* current arg information */
|
||||
"changes the ABI");
|
||||
}
|
||||
if (cum->sse_nregs)
|
||||
ret = gen_rtx_REG (mode, cum->sse_regno + FIRST_SSE_REG);
|
||||
ret = gen_reg_or_parallel (mode, TImode, orig_mode,
|
||||
cum->sse_regno + FIRST_SSE_REG);
|
||||
}
|
||||
break;
|
||||
case V8QImode:
|
||||
@ -2644,7 +2679,8 @@ function_arg (CUMULATIVE_ARGS *cum, /* current arg information */
|
||||
"changes the ABI");
|
||||
}
|
||||
if (cum->mmx_nregs)
|
||||
ret = gen_rtx_REG (mode, cum->mmx_regno + FIRST_MMX_REG);
|
||||
ret = gen_reg_or_parallel (mode, DImode, orig_mode,
|
||||
cum->mmx_regno + FIRST_MMX_REG);
|
||||
}
|
||||
break;
|
||||
}
|
||||
@ -4319,6 +4355,12 @@ aligned_operand (rtx op, enum machine_mode mode)
|
||||
/* Didn't find one -- this must be an aligned address. */
|
||||
return 1;
|
||||
}
|
||||
|
||||
int
|
||||
compare_operator (rtx op, enum machine_mode mode ATTRIBUTE_UNUSED)
|
||||
{
|
||||
return GET_CODE (op) == COMPARE;
|
||||
}
|
||||
|
||||
/* Initialize the table of extra 80387 mathematical constants. */
|
||||
|
||||
@ -5775,45 +5817,40 @@ ix86_find_base_term (rtx x)
|
||||
bool
|
||||
legitimate_constant_p (rtx x)
|
||||
{
|
||||
rtx inner;
|
||||
|
||||
switch (GET_CODE (x))
|
||||
{
|
||||
case SYMBOL_REF:
|
||||
/* TLS symbols are not constant. */
|
||||
if (tls_symbolic_operand (x, Pmode))
|
||||
return false;
|
||||
break;
|
||||
|
||||
case CONST:
|
||||
inner = XEXP (x, 0);
|
||||
x = XEXP (x, 0);
|
||||
|
||||
/* Offsets of TLS symbols are never valid.
|
||||
Discourage CSE from creating them. */
|
||||
if (GET_CODE (inner) == PLUS
|
||||
&& tls_symbolic_operand (XEXP (inner, 0), Pmode))
|
||||
return false;
|
||||
|
||||
if (GET_CODE (inner) == PLUS
|
||||
|| GET_CODE (inner) == MINUS)
|
||||
if (GET_CODE (x) == PLUS)
|
||||
{
|
||||
if (GET_CODE (XEXP (inner, 1)) != CONST_INT)
|
||||
if (GET_CODE (XEXP (x, 1)) != CONST_INT)
|
||||
return false;
|
||||
inner = XEXP (inner, 0);
|
||||
x = XEXP (x, 0);
|
||||
}
|
||||
|
||||
/* Only some unspecs are valid as "constants". */
|
||||
if (GET_CODE (inner) == UNSPEC)
|
||||
switch (XINT (inner, 1))
|
||||
if (GET_CODE (x) == UNSPEC)
|
||||
switch (XINT (x, 1))
|
||||
{
|
||||
case UNSPEC_TPOFF:
|
||||
case UNSPEC_NTPOFF:
|
||||
return local_exec_symbolic_operand (XVECEXP (inner, 0, 0), Pmode);
|
||||
return local_exec_symbolic_operand (XVECEXP (x, 0, 0), Pmode);
|
||||
case UNSPEC_DTPOFF:
|
||||
return local_dynamic_symbolic_operand (XVECEXP (inner, 0, 0), Pmode);
|
||||
return local_dynamic_symbolic_operand (XVECEXP (x, 0, 0), Pmode);
|
||||
default:
|
||||
return false;
|
||||
}
|
||||
|
||||
/* We must have drilled down to a symbol. */
|
||||
if (!symbolic_operand (x, Pmode))
|
||||
return false;
|
||||
/* FALLTHRU */
|
||||
|
||||
case SYMBOL_REF:
|
||||
/* TLS symbols are never valid. */
|
||||
if (tls_symbolic_operand (x, Pmode))
|
||||
return false;
|
||||
break;
|
||||
|
||||
default:
|
||||
@ -10609,10 +10646,11 @@ ix86_split_to_parts (rtx operand, rtx *parts, enum machine_mode mode)
|
||||
else if (GET_CODE (operand) == CONST_DOUBLE)
|
||||
{
|
||||
REAL_VALUE_TYPE r;
|
||||
long l[3];
|
||||
long l[4];
|
||||
|
||||
REAL_VALUE_FROM_CONST_DOUBLE (r, operand);
|
||||
real_to_target (l, &r, mode);
|
||||
|
||||
/* Do not use shift by 32 to avoid warning on 32bit systems. */
|
||||
if (HOST_BITS_PER_WIDE_INT >= 64)
|
||||
parts[0]
|
||||
@ -10622,6 +10660,7 @@ ix86_split_to_parts (rtx operand, rtx *parts, enum machine_mode mode)
|
||||
DImode);
|
||||
else
|
||||
parts[0] = immed_double_const (l[0], l[1], DImode);
|
||||
|
||||
if (upper_mode == SImode)
|
||||
parts[1] = gen_int_mode (l[2], SImode);
|
||||
else if (HOST_BITS_PER_WIDE_INT >= 64)
|
||||
@ -14896,10 +14935,29 @@ ix86_hard_regno_mode_ok (int regno, enum machine_mode mode)
|
||||
if (FP_REGNO_P (regno))
|
||||
return VALID_FP_MODE_P (mode);
|
||||
if (SSE_REGNO_P (regno))
|
||||
return (TARGET_SSE ? VALID_SSE_REG_MODE (mode) : 0);
|
||||
{
|
||||
/* HACK! We didn't change all of the constraints for SSE1 for the
|
||||
scalar modes on the branch. Fortunately, they're not required
|
||||
for ABI compatibility. */
|
||||
if (!TARGET_SSE2 && !VECTOR_MODE_P (mode))
|
||||
return VALID_SSE_REG_MODE (mode);
|
||||
|
||||
/* We implement the move patterns for all vector modes into and
|
||||
out of SSE registers, even when no operation instructions
|
||||
are available. */
|
||||
return (VALID_SSE_REG_MODE (mode)
|
||||
|| VALID_SSE2_REG_MODE (mode)
|
||||
|| VALID_MMX_REG_MODE (mode)
|
||||
|| VALID_MMX_REG_MODE_3DNOW (mode));
|
||||
}
|
||||
if (MMX_REGNO_P (regno))
|
||||
return (TARGET_MMX
|
||||
? VALID_MMX_REG_MODE (mode) || VALID_MMX_REG_MODE_3DNOW (mode) : 0);
|
||||
{
|
||||
/* We implement the move patterns for 3DNOW modes even in MMX mode,
|
||||
so if the register is available at all, then we can move data of
|
||||
the given mode into or out of it. */
|
||||
return (VALID_MMX_REG_MODE (mode)
|
||||
|| VALID_MMX_REG_MODE_3DNOW (mode));
|
||||
}
|
||||
/* We handle both integer and floats in the general purpose registers.
|
||||
In future we should be able to handle vector modes as well. */
|
||||
if (!VALID_INT_MODE_P (mode) && !VALID_FP_MODE_P (mode))
|
||||
@ -15235,7 +15293,9 @@ ix86_rtx_costs (rtx x, int code, int outer_code, int *total)
|
||||
return false;
|
||||
|
||||
case FLOAT_EXTEND:
|
||||
if (!TARGET_SSE_MATH || !VALID_SSE_REG_MODE (mode))
|
||||
if (!TARGET_SSE_MATH
|
||||
|| mode == XFmode
|
||||
|| (mode == DFmode && !TARGET_SSE2))
|
||||
*total = 0;
|
||||
return false;
|
||||
|
||||
|
@ -447,6 +447,10 @@ extern int x86_prefetch_sse;
|
||||
redefines this to 1. */
|
||||
#define TARGET_MACHO 0
|
||||
|
||||
/* Subtargets may reset this to 1 in order to enable 96-bit long double
|
||||
with the rounding mode forced to 53 bits. */
|
||||
#define TARGET_96_ROUND_53_LONG_DOUBLE 0
|
||||
|
||||
/* This macro is similar to `TARGET_SWITCHES' but defines names of
|
||||
command options that have values. Its definition is an
|
||||
initializer with a subgrouping for each command option.
|
||||
@ -1059,14 +1063,11 @@ do { \
|
||||
|
||||
#define VALID_SSE2_REG_MODE(MODE) \
|
||||
((MODE) == V16QImode || (MODE) == V8HImode || (MODE) == V2DFmode \
|
||||
|| (MODE) == V2DImode)
|
||||
|| (MODE) == V2DImode || (MODE) == DFmode)
|
||||
|
||||
#define VALID_SSE_REG_MODE(MODE) \
|
||||
((MODE) == TImode || (MODE) == V4SFmode || (MODE) == V4SImode \
|
||||
|| (MODE) == SFmode || (MODE) == TFmode \
|
||||
/* Always accept SSE2 modes so that xmmintrin.h compiles. */ \
|
||||
|| VALID_SSE2_REG_MODE (MODE) \
|
||||
|| (TARGET_SSE2 && ((MODE) == DFmode || VALID_MMX_REG_MODE (MODE))))
|
||||
|| (MODE) == SFmode || (MODE) == TFmode)
|
||||
|
||||
#define VALID_MMX_REG_MODE_3DNOW(MODE) \
|
||||
((MODE) == V2SFmode || (MODE) == SFmode)
|
||||
@ -2990,7 +2991,8 @@ do { \
|
||||
{"zero_extended_scalar_load_operand", {MEM}}, \
|
||||
{"vector_move_operand", {CONST_VECTOR, SUBREG, REG, MEM}}, \
|
||||
{"no_seg_address_operand", {CONST_INT, CONST_DOUBLE, CONST, SYMBOL_REF, \
|
||||
LABEL_REF, SUBREG, REG, MEM, PLUS, MULT}},
|
||||
LABEL_REF, SUBREG, REG, MEM, PLUS, MULT}}, \
|
||||
{"compare_operator", {COMPARE}},
|
||||
|
||||
/* A list of predicates that do special things with modes, and so
|
||||
should not elicit warnings for VOIDmode match_operand. */
|
||||
|
File diff suppressed because it is too large
Load Diff
@ -36,17 +36,17 @@ xp-bit.c: $(srcdir)/config/fp-bit.c
|
||||
echo '#define EXTENDED_FLOAT_STUBS' > xp-bit.c
|
||||
cat $(srcdir)/config/fp-bit.c >> xp-bit.c
|
||||
|
||||
MULTILIB_OPTIONS = mcpu=i486/mcpu=pentium/mcpu=pentiumpro/mcpu=k6/mcpu=athlon \
|
||||
MULTILIB_OPTIONS = mtune=i486/mtune=pentium/mtune=pentiumpro/mtune=k6/mtune=athlon \
|
||||
msoft-float mno-fp-ret-in-387
|
||||
MULTILIB_DIRNAMES= m486 mpentium mpentiumpro k6 athlon soft-float nofp
|
||||
MULTILIB_MATCHES = msoft-float=mno-m80387
|
||||
MULTILIB_EXCEPTIONS = \
|
||||
mno-fp-ret-in-387 \
|
||||
mcpu=i486/*mno-fp-ret-in-387* \
|
||||
mcpu=pentium/*msoft-float* mcpu=pentium/*mno-fp-ret-in-387* \
|
||||
mcpu=pentiumpro/*msoft-float* mcpu=pentiumpro/*mno-fp-ret-in-387* \
|
||||
mcpu=k6/*msoft-float* mcpu=k6/*mno-fp-ret-in-387* \
|
||||
mcpu=athlon/*msoft-float* mcpu=athlon/*mno-fp-ret-in-387*
|
||||
mtune=i486/*mno-fp-ret-in-387* \
|
||||
mtune=pentium/*msoft-float* mtune=pentium/*mno-fp-ret-in-387* \
|
||||
mtune=pentiumpro/*msoft-float* mtune=pentiumpro/*mno-fp-ret-in-387* \
|
||||
mtune=k6/*msoft-float* mtune=k6/*mno-fp-ret-in-387* \
|
||||
mtune=athlon/*msoft-float* mtune=athlon/*mno-fp-ret-in-387*
|
||||
|
||||
EXTRA_MULTILIB_PARTS = crtbegin.o crtend.o
|
||||
|
||||
|
@ -38,10 +38,10 @@
|
||||
#include <mmintrin.h>
|
||||
|
||||
/* The data type intended for user use. */
|
||||
typedef int __m128 __attribute__ ((__mode__(__V4SF__)));
|
||||
typedef float __m128 __attribute__ ((__mode__(__V4SF__)));
|
||||
|
||||
/* Internal data types for implementing the intrinsics. */
|
||||
typedef int __v4sf __attribute__ ((__mode__(__V4SF__)));
|
||||
typedef float __v4sf __attribute__ ((__mode__(__V4SF__)));
|
||||
|
||||
/* Create a selector for use with the SHUFPS instruction. */
|
||||
#define _MM_SHUFFLE(fp3,fp2,fp1,fp0) \
|
||||
|
@ -390,20 +390,55 @@ call_operand (rtx op, enum machine_mode mode)
|
||||
int
|
||||
sdata_symbolic_operand (rtx op, enum machine_mode mode ATTRIBUTE_UNUSED)
|
||||
{
|
||||
HOST_WIDE_INT offset = 0, size = 0;
|
||||
|
||||
switch (GET_CODE (op))
|
||||
{
|
||||
case CONST:
|
||||
if (GET_CODE (XEXP (op, 0)) != PLUS
|
||||
|| GET_CODE (XEXP (XEXP (op, 0), 0)) != SYMBOL_REF)
|
||||
op = XEXP (op, 0);
|
||||
if (GET_CODE (op) != PLUS
|
||||
|| GET_CODE (XEXP (op, 0)) != SYMBOL_REF
|
||||
|| GET_CODE (XEXP (op, 1)) != CONST_INT)
|
||||
break;
|
||||
op = XEXP (XEXP (op, 0), 0);
|
||||
offset = INTVAL (XEXP (op, 1));
|
||||
op = XEXP (op, 0);
|
||||
/* FALLTHRU */
|
||||
|
||||
case SYMBOL_REF:
|
||||
if (CONSTANT_POOL_ADDRESS_P (op))
|
||||
return GET_MODE_SIZE (get_pool_mode (op)) <= ia64_section_threshold;
|
||||
{
|
||||
size = GET_MODE_SIZE (get_pool_mode (op));
|
||||
if (size > ia64_section_threshold)
|
||||
return false;
|
||||
}
|
||||
else
|
||||
return SYMBOL_REF_LOCAL_P (op) && SYMBOL_REF_SMALL_P (op);
|
||||
{
|
||||
tree t;
|
||||
|
||||
if (!SYMBOL_REF_LOCAL_P (op) || !SYMBOL_REF_SMALL_P (op))
|
||||
return false;
|
||||
|
||||
/* Note that in addition to DECLs, we can get various forms
|
||||
of constants here. */
|
||||
t = SYMBOL_REF_DECL (op);
|
||||
if (DECL_P (t))
|
||||
t = DECL_SIZE_UNIT (t);
|
||||
else
|
||||
t = TYPE_SIZE_UNIT (TREE_TYPE (t));
|
||||
if (t && host_integerp (t, 0))
|
||||
{
|
||||
size = tree_low_cst (t, 0);
|
||||
if (size < 0)
|
||||
size = 0;
|
||||
}
|
||||
}
|
||||
|
||||
/* Deny the stupid user trick of addressing outside the object. Such
|
||||
things quickly result in GPREL22 relocation overflows. Of course,
|
||||
they're also highly undefined. From a pure pedant's point of view
|
||||
they deserve a slap on the wrist (such as provided by a relocation
|
||||
overflow), but that just leads to bugzilla noise. */
|
||||
return (offset >= 0 && offset <= size);
|
||||
|
||||
default:
|
||||
break;
|
||||
@ -3154,10 +3189,13 @@ ia64_expand_epilogue (int sibcall_p)
|
||||
preserve those input registers used as arguments to the sibling call.
|
||||
It is unclear how to compute that number here. */
|
||||
if (current_frame_info.n_input_regs != 0)
|
||||
emit_insn (gen_alloc (gen_rtx_REG (DImode, fp),
|
||||
GEN_INT (0), GEN_INT (0),
|
||||
GEN_INT (current_frame_info.n_input_regs),
|
||||
GEN_INT (0)));
|
||||
{
|
||||
rtx n_inputs = GEN_INT (current_frame_info.n_input_regs);
|
||||
insn = emit_insn (gen_alloc (gen_rtx_REG (DImode, fp),
|
||||
const0_rtx, const0_rtx,
|
||||
n_inputs, const0_rtx));
|
||||
RTX_FRAME_RELATED_P (insn) = 1;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -3283,15 +3321,16 @@ static bool
|
||||
ia64_assemble_integer (rtx x, unsigned int size, int aligned_p)
|
||||
{
|
||||
if (size == POINTER_SIZE / BITS_PER_UNIT
|
||||
&& aligned_p
|
||||
&& !(TARGET_NO_PIC || TARGET_AUTO_PIC)
|
||||
&& GET_CODE (x) == SYMBOL_REF
|
||||
&& SYMBOL_REF_FUNCTION_P (x))
|
||||
{
|
||||
if (POINTER_SIZE == 32)
|
||||
fputs ("\tdata4\t@fptr(", asm_out_file);
|
||||
else
|
||||
fputs ("\tdata8\t@fptr(", asm_out_file);
|
||||
static const char * const directive[2][2] = {
|
||||
/* 64-bit pointer */ /* 32-bit pointer */
|
||||
{ "\tdata8.ua\t@fptr(", "\tdata4.ua\t@fptr("}, /* unaligned */
|
||||
{ "\tdata8\t@fptr(", "\tdata4\t@fptr("} /* aligned */
|
||||
};
|
||||
fputs (directive[(aligned_p != 0)][POINTER_SIZE == 32], asm_out_file);
|
||||
output_addr_const (asm_out_file, x);
|
||||
fputs (")\n", asm_out_file);
|
||||
return true;
|
||||
@ -3917,6 +3956,12 @@ ia64_function_arg_pass_by_reference (CUMULATIVE_ARGS *cum ATTRIBUTE_UNUSED,
|
||||
static bool
|
||||
ia64_function_ok_for_sibcall (tree decl, tree exp ATTRIBUTE_UNUSED)
|
||||
{
|
||||
/* We can't perform a sibcall if the current function has the syscall_linkage
|
||||
attribute. */
|
||||
if (lookup_attribute ("syscall_linkage",
|
||||
TYPE_ATTRIBUTES (TREE_TYPE (current_function_decl))))
|
||||
return false;
|
||||
|
||||
/* We must always return with our current GP. This means we can
|
||||
only sibcall to functions defined in the current module. */
|
||||
return decl && (*targetm.binds_local_p) (decl);
|
||||
@ -7782,13 +7827,24 @@ process_set (FILE *asm_out_file, rtx pat)
|
||||
{
|
||||
dest_regno = REGNO (dest);
|
||||
|
||||
/* If this isn't the final destination for ar.pfs, the alloc
|
||||
shouldn't have been marked frame related. */
|
||||
if (dest_regno != current_frame_info.reg_save_ar_pfs)
|
||||
abort ();
|
||||
|
||||
fprintf (asm_out_file, "\t.save ar.pfs, r%d\n",
|
||||
ia64_dbx_register_number (dest_regno));
|
||||
/* If this is the final destination for ar.pfs, then this must
|
||||
be the alloc in the prologue. */
|
||||
if (dest_regno == current_frame_info.reg_save_ar_pfs)
|
||||
fprintf (asm_out_file, "\t.save ar.pfs, r%d\n",
|
||||
ia64_dbx_register_number (dest_regno));
|
||||
else
|
||||
{
|
||||
/* This must be an alloc before a sibcall. We must drop the
|
||||
old frame info. The easiest way to drop the old frame
|
||||
info is to ensure we had a ".restore sp" directive
|
||||
followed by a new prologue. If the procedure doesn't
|
||||
have a memory-stack frame, we'll issue a dummy ".restore
|
||||
sp" now. */
|
||||
if (current_frame_info.total_size == 0 && !frame_pointer_needed)
|
||||
/* if haven't done process_epilogue() yet, do it now */
|
||||
process_epilogue ();
|
||||
fprintf (asm_out_file, "\t.prologue\n");
|
||||
}
|
||||
return 1;
|
||||
}
|
||||
|
||||
|
@ -1 +1,3 @@
|
||||
LIB2ADDEH += $(srcdir)/config/ia64/fde-glibc.c
|
||||
# Use system libunwind library on IA-64 GLIBC based system.
|
||||
LIB2ADDEH = $(srcdir)/unwind-sjlj.c $(srcdir)/unwind-c.c \
|
||||
$(srcdir)/unwind-compat.c
|
||||
|
4
contrib/gcc/config/ia64/t-glibc-libunwind
Normal file
4
contrib/gcc/config/ia64/t-glibc-libunwind
Normal file
@ -0,0 +1,4 @@
|
||||
# Build libunwind for IA-64 GLIBC based system.
|
||||
LIBUNWIND = $(srcdir)/config/ia64/fde-glibc.c \
|
||||
$(srcdir)/config/ia64/unwind-ia64.c
|
||||
LIBUNWINDDEP = unwind.inc
|
@ -23,6 +23,8 @@ LIBGCC1_TEST =
|
||||
# We do not want to include the EH stuff that linux uses, we want to use
|
||||
# the HP-UX libunwind library.
|
||||
|
||||
T_CFLAGS += -DUSE_LIBUNWIND_EXCEPTIONS
|
||||
|
||||
LIB2ADDEH =
|
||||
|
||||
SHLIB_EXT = .so
|
||||
|
@ -37,6 +37,7 @@
|
||||
#include "tm.h"
|
||||
#include "unwind.h"
|
||||
#include "unwind-ia64.h"
|
||||
#include "unwind-compat.h"
|
||||
#include "ia64intrin.h"
|
||||
|
||||
/* This isn't thread safe, but nice for occasional tests. */
|
||||
@ -2274,6 +2275,8 @@ uw_install_context (struct _Unwind_Context *current __attribute__((unused)),
|
||||
"(p6) ldf.fill f22 = [r28] \n\t"
|
||||
"cmp.ne p7, p0 = r0, r29 \n\t"
|
||||
";; \n\t"
|
||||
"ld8 r27 = [r20], 8 \n\t"
|
||||
";; \n\t"
|
||||
"ld8 r28 = [r20], 8 \n\t"
|
||||
"(p7) ldf.fill f23 = [r29] \n\t"
|
||||
"cmp.ne p6, p0 = r0, r22 \n\t"
|
||||
@ -2381,4 +2384,24 @@ uw_identify_context (struct _Unwind_Context *context)
|
||||
}
|
||||
|
||||
#include "unwind.inc"
|
||||
|
||||
#if defined (USE_GAS_SYMVER) && defined (SHARED) && defined (USE_LIBUNWIND_EXCEPTIONS)
|
||||
alias (_Unwind_Backtrace);
|
||||
alias (_Unwind_DeleteException);
|
||||
alias (_Unwind_FindEnclosingFunction);
|
||||
alias (_Unwind_FindTableEntry);
|
||||
alias (_Unwind_ForcedUnwind);
|
||||
alias (_Unwind_GetBSP);
|
||||
alias (_Unwind_GetCFA);
|
||||
alias (_Unwind_GetGR);
|
||||
alias (_Unwind_GetIP);
|
||||
alias (_Unwind_GetLanguageSpecificData);
|
||||
alias (_Unwind_GetRegionStart);
|
||||
alias (_Unwind_RaiseException);
|
||||
alias (_Unwind_Resume);
|
||||
alias (_Unwind_Resume_or_Rethrow);
|
||||
alias (_Unwind_SetGR);
|
||||
alias (_Unwind_SetIP);
|
||||
#endif
|
||||
|
||||
#endif
|
||||
|
@ -28,4 +28,5 @@ struct unw_table_entry
|
||||
|
||||
extern struct unw_table_entry *
|
||||
_Unwind_FindTableEntry (void *pc, unsigned long *segment_base,
|
||||
unsigned long *gp);
|
||||
unsigned long *gp)
|
||||
__attribute__ ((__visibility__ ("hidden")));
|
||||
|
@ -1,6 +1,6 @@
|
||||
/* Definitions of target machine for GNU compiler,
|
||||
for IBM RS/6000 POWER running AIX.
|
||||
Copyright (C) 2000, 2001, 2002, 2003, 2004 Free Software Foundation, Inc.
|
||||
Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GCC.
|
||||
|
||||
@ -175,15 +175,15 @@
|
||||
#define JUMP_TABLES_IN_TEXT_SECTION 1
|
||||
|
||||
/* Enable AIX XL compiler calling convention breakage compatibility. */
|
||||
#undef TARGET_XL_CALL
|
||||
#define MASK_XL_CALL 0x40000000
|
||||
#define TARGET_XL_CALL (target_flags & MASK_XL_CALL)
|
||||
#undef TARGET_XL_COMPAT
|
||||
#define MASK_XL_COMPAT 0x40000000
|
||||
#define TARGET_XL_COMPAT (target_flags & MASK_XL_COMPAT)
|
||||
#undef SUBTARGET_SWITCHES
|
||||
#define SUBTARGET_SWITCHES \
|
||||
{"xl-call", MASK_XL_CALL, \
|
||||
N_("Always pass floating-point arguments in memory") }, \
|
||||
{"no-xl-call", - MASK_XL_CALL, \
|
||||
N_("Don't always pass floating-point arguments in memory") }, \
|
||||
{"xl-compat", MASK_XL_COMPAT, \
|
||||
N_("Conform more closely to IBM XLC semantics") }, \
|
||||
{"no-xl-compat", - MASK_XL_COMPAT, \
|
||||
N_("Default GCC semantics that differ from IBM XLC") }, \
|
||||
SUBSUBTARGET_SWITCHES
|
||||
#define SUBSUBTARGET_SWITCHES
|
||||
|
||||
@ -209,7 +209,7 @@
|
||||
code that does the save/restore is generated by the linker, so
|
||||
we have no good way to determine at compile time what to do. */
|
||||
|
||||
#ifdef __powerpc64__
|
||||
#ifdef __64BIT__
|
||||
#define MD_FROB_UPDATE_CONTEXT(CTX, FS) \
|
||||
do { \
|
||||
if ((FS)->regs.reg[2].how == REG_UNSAVED) \
|
||||
|
@ -98,3 +98,7 @@
|
||||
#undef RS6000_CALL_GLUE
|
||||
#define RS6000_CALL_GLUE "{cror 31,31,31|nop}"
|
||||
|
||||
/* The IBM AIX 4.x assembler doesn't support forward references in
|
||||
.set directives. We handle this by deferring the output of .set
|
||||
directives to the end of the compilation unit. */
|
||||
#define TARGET_DEFERRED_OUTPUT_DEFS(DECL,TARGET) true
|
||||
|
@ -187,3 +187,8 @@ do { \
|
||||
|
||||
#undef LD_INIT_SWITCH
|
||||
#define LD_INIT_SWITCH "-binitfini"
|
||||
|
||||
/* The IBM AIX 4.x assembler doesn't support forward references in
|
||||
.set directives. We handle this by deferring the output of .set
|
||||
directives to the end of the compilation unit. */
|
||||
#define TARGET_DEFERRED_OUTPUT_DEFS(DECL,TARGET) true
|
||||
|
@ -193,3 +193,7 @@ do { \
|
||||
#undef TARGET_C99_FUNCTIONS
|
||||
#define TARGET_C99_FUNCTIONS 1
|
||||
|
||||
#ifndef _AIX52
|
||||
extern long long int atoll(const char *);
|
||||
#endif
|
||||
|
||||
|
File diff suppressed because it is too large
Load Diff
@ -594,9 +594,9 @@
|
||||
;; Fused multiply subtract
|
||||
(define_insn "altivec_vnmsubfp"
|
||||
[(set (match_operand:V4SF 0 "register_operand" "=v")
|
||||
(minus:V4SF (mult:V4SF (match_operand:V4SF 1 "register_operand" "v")
|
||||
(neg:V4SF (minus:V4SF (mult:V4SF (match_operand:V4SF 1 "register_operand" "v")
|
||||
(match_operand:V4SF 2 "register_operand" "v"))
|
||||
(match_operand:V4SF 3 "register_operand" "v")))]
|
||||
(match_operand:V4SF 3 "register_operand" "v"))))]
|
||||
"TARGET_ALTIVEC"
|
||||
"vnmsubfp %0,%1,%2,%3"
|
||||
[(set_attr "type" "vecfloat")])
|
||||
|
@ -23,18 +23,6 @@
|
||||
#undef TARGET_VERSION
|
||||
#define TARGET_VERSION fprintf (stderr, " (BeOS/PowerPC)");
|
||||
|
||||
/* Enable AIX XL compiler calling convention breakage compatibility. */
|
||||
#define MASK_XL_CALL 0x40000000
|
||||
#define TARGET_XL_CALL (target_flags & MASK_XL_CALL)
|
||||
#undef SUBTARGET_SWITCHES
|
||||
#define SUBTARGET_SWITCHES \
|
||||
{"xl-call", MASK_XL_CALL, \
|
||||
N_("Always pass floating-point arguments in memory") }, \
|
||||
{"no-xl-call", - MASK_XL_CALL, \
|
||||
N_("Don't always pass floating-point arguments in memory") }, \
|
||||
{"threads", 0}, \
|
||||
{"pe", 0},
|
||||
|
||||
#undef ASM_SPEC
|
||||
#define ASM_SPEC "-u %(asm_cpu)"
|
||||
|
||||
|
2
contrib/gcc/config/rs6000/darwin-ldouble-shared.c
Normal file
2
contrib/gcc/config/rs6000/darwin-ldouble-shared.c
Normal file
@ -0,0 +1,2 @@
|
||||
#define IN_LIBGCC2_S 1
|
||||
#include "darwin-ldouble.c"
|
@ -1,5 +1,5 @@
|
||||
/* 128-bit long double support routines for Darwin.
|
||||
Copyright (C) 1993, 2003, 2004 Free Software Foundation, Inc.
|
||||
Copyright (C) 1993, 2003, 2004, 2005 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GCC.
|
||||
|
||||
@ -48,7 +48,7 @@ Software Foundation, 59 Temple Place - Suite 330, Boston, MA
|
||||
|
||||
This code currently assumes big-endian. */
|
||||
|
||||
#if !_SOFT_FLOAT && (defined (__MACH__) || defined (__powerpc64__))
|
||||
#if !_SOFT_FLOAT && (defined (__MACH__) || defined (__powerpc64__) || defined (_AIX))
|
||||
|
||||
#define fabs(x) __builtin_fabs(x)
|
||||
|
||||
@ -58,10 +58,27 @@ Software Foundation, 59 Temple Place - Suite 330, Boston, MA
|
||||
but GCC currently generates poor code when a union is used to turn
|
||||
a long double into a pair of doubles. */
|
||||
|
||||
extern long double _xlqadd (double, double, double, double);
|
||||
extern long double _xlqsub (double, double, double, double);
|
||||
extern long double _xlqmul (double, double, double, double);
|
||||
extern long double _xlqdiv (double, double, double, double);
|
||||
extern long double __gcc_qadd (double, double, double, double);
|
||||
extern long double __gcc_qsub (double, double, double, double);
|
||||
extern long double __gcc_qmul (double, double, double, double);
|
||||
extern long double __gcc_qdiv (double, double, double, double);
|
||||
|
||||
#if defined __ELF__ && defined IN_LIBGCC2_S
|
||||
/* Provide definitions of the old symbol names to statisfy apps and
|
||||
shared libs built against an older libgcc. To access the _xlq
|
||||
symbols an explicit version reference is needed, so these won't
|
||||
satisfy an unadorned reference like _xlqadd. If dot symbols are
|
||||
not needed, the assembler will remove the aliases from the symbol
|
||||
table. */
|
||||
__asm__ (".symver __gcc_qadd,_xlqadd@GCC_3.4\n\t"
|
||||
".symver __gcc_qsub,_xlqsub@GCC_3.4\n\t"
|
||||
".symver __gcc_qmul,_xlqmul@GCC_3.4\n\t"
|
||||
".symver __gcc_qdiv,_xlqdiv@GCC_3.4\n\t"
|
||||
".symver .__gcc_qadd,._xlqadd@GCC_3.4\n\t"
|
||||
".symver .__gcc_qsub,._xlqsub@GCC_3.4\n\t"
|
||||
".symver .__gcc_qmul,._xlqmul@GCC_3.4\n\t"
|
||||
".symver .__gcc_qdiv,._xlqdiv@GCC_3.4");
|
||||
#endif
|
||||
|
||||
typedef union
|
||||
{
|
||||
@ -73,7 +90,7 @@ static const double FPKINF = 1.0/0.0;
|
||||
|
||||
/* Add two 'long double' values and return the result. */
|
||||
long double
|
||||
_xlqadd (double a, double b, double c, double d)
|
||||
__gcc_qadd (double a, double b, double c, double d)
|
||||
{
|
||||
longDblUnion z;
|
||||
double t, tau, u, FPR_zero, FPR_PosInf;
|
||||
@ -132,13 +149,13 @@ _xlqadd (double a, double b, double c, double d)
|
||||
}
|
||||
|
||||
long double
|
||||
_xlqsub (double a, double b, double c, double d)
|
||||
__gcc_qsub (double a, double b, double c, double d)
|
||||
{
|
||||
return _xlqadd (a, b, -c, -d);
|
||||
return __gcc_qadd (a, b, -c, -d);
|
||||
}
|
||||
|
||||
long double
|
||||
_xlqmul (double a, double b, double c, double d)
|
||||
__gcc_qmul (double a, double b, double c, double d)
|
||||
{
|
||||
longDblUnion z;
|
||||
double t, tau, u, v, w, FPR_zero, FPR_PosInf;
|
||||
@ -169,7 +186,7 @@ _xlqmul (double a, double b, double c, double d)
|
||||
}
|
||||
|
||||
long double
|
||||
_xlqdiv (double a, double b, double c, double d)
|
||||
__gcc_qdiv (double a, double b, double c, double d)
|
||||
{
|
||||
longDblUnion z;
|
||||
double s, sigma, t, tau, u, v, w, FPR_zero, FPR_PosInf;
|
||||
|
@ -111,6 +111,13 @@ do { \
|
||||
#define SUBTARGET_EXTRA_SPECS \
|
||||
{ "darwin_arch", "ppc" },
|
||||
|
||||
/* The "-faltivec" option should have been called "-maltivec" all along. */
|
||||
#define SUBTARGET_OPTION_TRANSLATE_TABLE \
|
||||
{ "-faltivec", "-maltivec -include altivec.h" }, \
|
||||
{ "-fno-altivec", "-mno-altivec" }, \
|
||||
{ "-Waltivec-long-deprecated", "-mwarn-altivec-long" }, \
|
||||
{ "-Wno-altivec-long-deprecated", "-mno-warn-altivec-long" }
|
||||
|
||||
/* Make both r2 and r3 available for allocation. */
|
||||
#define FIXED_R2 0
|
||||
#define FIXED_R13 0
|
||||
|
@ -252,7 +252,7 @@ FUNC_START(__eabi_convert)
|
||||
|
||||
.Lcvt:
|
||||
lwzu 6,4(3) /* pointer to convert */
|
||||
cmpi 0,6,0
|
||||
cmpwi 0,6,0
|
||||
beq- .Lcvt2 /* if pointer is null, don't convert */
|
||||
|
||||
add 6,6,12 /* convert pointer */
|
||||
|
@ -1,7 +1,7 @@
|
||||
GCC_3.4 {
|
||||
GCC_3.4.4 {
|
||||
# long double support
|
||||
_xlqadd
|
||||
_xlqsub
|
||||
_xlqmul
|
||||
_xlqdiv
|
||||
__gcc_qadd
|
||||
__gcc_qsub
|
||||
__gcc_qmul
|
||||
__gcc_qdiv
|
||||
}
|
||||
|
322
contrib/gcc/config/rs6000/linux-unwind.h
Normal file
322
contrib/gcc/config/rs6000/linux-unwind.h
Normal file
@ -0,0 +1,322 @@
|
||||
/* DWARF2 EH unwinding support for PowerPC and PowerPC64 Linux.
|
||||
Copyright (C) 2004, 2005 Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GCC.
|
||||
|
||||
GCC is free software; you can redistribute it and/or modify it
|
||||
under the terms of the GNU General Public License as published
|
||||
by the Free Software Foundation; either version 2, or (at your
|
||||
option) any later version.
|
||||
|
||||
In addition to the permissions in the GNU General Public License,
|
||||
the Free Software Foundation gives you unlimited permission to link
|
||||
the compiled version of this file with other programs, and to
|
||||
distribute those programs without any restriction coming from the
|
||||
use of this file. (The General Public License restrictions do
|
||||
apply in other respects; for example, they cover modification of
|
||||
the file, and distribution when not linked into another program.)
|
||||
|
||||
GCC is distributed in the hope that it will be useful, but WITHOUT
|
||||
ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
|
||||
or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public
|
||||
License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with GCC; see the file COPYING. If not, write to the
|
||||
Free Software Foundation, 59 Temple Place - Suite 330, Boston,
|
||||
MA 02111-1307, USA. */
|
||||
|
||||
/* This file defines our own versions of various kernel and user
|
||||
structs, so that system headers are not needed, which otherwise
|
||||
can make bootstrapping a new toolchain difficult. Do not use
|
||||
these structs elsewhere; Many fields are missing, particularly
|
||||
from the end of the structures. */
|
||||
|
||||
struct gcc_vregs
|
||||
{
|
||||
__attribute__ ((vector_size (16))) int vr[32];
|
||||
#ifdef __powerpc64__
|
||||
unsigned int pad1[3];
|
||||
unsigned int vscr;
|
||||
unsigned int vsave;
|
||||
unsigned int pad2[3];
|
||||
#else
|
||||
unsigned int vsave;
|
||||
unsigned int pad[2];
|
||||
unsigned int vscr;
|
||||
#endif
|
||||
};
|
||||
|
||||
struct gcc_regs
|
||||
{
|
||||
unsigned long gpr[32];
|
||||
unsigned long nip;
|
||||
unsigned long msr;
|
||||
unsigned long orig_gpr3;
|
||||
unsigned long ctr;
|
||||
unsigned long link;
|
||||
unsigned long xer;
|
||||
unsigned long ccr;
|
||||
unsigned long softe;
|
||||
unsigned long trap;
|
||||
unsigned long dar;
|
||||
unsigned long dsisr;
|
||||
unsigned long result;
|
||||
unsigned long pad1[4];
|
||||
double fpr[32];
|
||||
unsigned int pad2;
|
||||
unsigned int fpscr;
|
||||
#ifdef __powerpc64__
|
||||
struct gcc_vregs *vp;
|
||||
#else
|
||||
unsigned int pad3[2];
|
||||
#endif
|
||||
struct gcc_vregs vregs;
|
||||
};
|
||||
|
||||
struct gcc_ucontext
|
||||
{
|
||||
#ifdef __powerpc64__
|
||||
unsigned long pad[28];
|
||||
#else
|
||||
unsigned long pad[12];
|
||||
#endif
|
||||
struct gcc_regs *regs;
|
||||
struct gcc_regs rsave;
|
||||
};
|
||||
|
||||
#ifdef __powerpc64__
|
||||
|
||||
enum { SIGNAL_FRAMESIZE = 128 };
|
||||
|
||||
/* If the current unwind info (FS) does not contain explicit info
|
||||
saving R2, then we have to do a minor amount of code reading to
|
||||
figure out if it was saved. The big problem here is that the
|
||||
code that does the save/restore is generated by the linker, so
|
||||
we have no good way to determine at compile time what to do. */
|
||||
|
||||
#define MD_FROB_UPDATE_CONTEXT(CTX, FS) \
|
||||
do { \
|
||||
if ((FS)->regs.reg[2].how == REG_UNSAVED) \
|
||||
{ \
|
||||
unsigned int *insn \
|
||||
= (unsigned int *) \
|
||||
_Unwind_GetGR ((CTX), LINK_REGISTER_REGNUM); \
|
||||
if (*insn == 0xE8410028) \
|
||||
_Unwind_SetGRPtr ((CTX), 2, (CTX)->cfa + 40); \
|
||||
} \
|
||||
} while (0)
|
||||
|
||||
/* If PC is at a sigreturn trampoline, return a pointer to the
|
||||
regs. Otherwise return NULL. */
|
||||
|
||||
#define PPC_LINUX_GET_REGS(CONTEXT) \
|
||||
({ \
|
||||
const unsigned char *pc = (CONTEXT)->ra; \
|
||||
struct gcc_regs *regs = NULL; \
|
||||
\
|
||||
/* addi r1, r1, 128; li r0, 0x0077; sc (sigreturn) */ \
|
||||
/* addi r1, r1, 128; li r0, 0x00AC; sc (rt_sigreturn) */ \
|
||||
if (*(unsigned int *) (pc + 0) != 0x38210000 + SIGNAL_FRAMESIZE \
|
||||
|| *(unsigned int *) (pc + 8) != 0x44000002) \
|
||||
; \
|
||||
else if (*(unsigned int *) (pc + 4) == 0x38000077) \
|
||||
{ \
|
||||
struct sigframe { \
|
||||
char gap[SIGNAL_FRAMESIZE]; \
|
||||
unsigned long pad[7]; \
|
||||
struct gcc_regs *regs; \
|
||||
} *frame = (struct sigframe *) (CONTEXT)->cfa; \
|
||||
regs = frame->regs; \
|
||||
} \
|
||||
else if (*(unsigned int *) (pc + 4) == 0x380000AC) \
|
||||
{ \
|
||||
/* This works for 2.4 kernels, but not for 2.6 kernels with vdso \
|
||||
because pc isn't pointing into the stack. Can be removed when \
|
||||
no one is running 2.4.19 or 2.4.20, the first two ppc64 \
|
||||
kernels released. */ \
|
||||
struct rt_sigframe_24 { \
|
||||
int tramp[6]; \
|
||||
void *pinfo; \
|
||||
struct gcc_ucontext *puc; \
|
||||
} *frame24 = (struct rt_sigframe_24 *) pc; \
|
||||
\
|
||||
/* Test for magic value in *puc of vdso. */ \
|
||||
if ((long) frame24->puc != -21 * 8) \
|
||||
regs = frame24->puc->regs; \
|
||||
else \
|
||||
{ \
|
||||
/* This works for 2.4.21 and later kernels. */ \
|
||||
struct rt_sigframe { \
|
||||
char gap[SIGNAL_FRAMESIZE]; \
|
||||
struct gcc_ucontext uc; \
|
||||
unsigned long pad[2]; \
|
||||
int tramp[6]; \
|
||||
void *pinfo; \
|
||||
struct gcc_ucontext *puc; \
|
||||
} *frame = (struct rt_sigframe *) (CONTEXT)->cfa; \
|
||||
regs = frame->uc.regs; \
|
||||
} \
|
||||
} \
|
||||
regs; \
|
||||
})
|
||||
|
||||
#define LINUX_HWCAP_DEFAULT 0xc0000000
|
||||
|
||||
#define PPC_LINUX_VREGS(REGS) (REGS)->vp
|
||||
|
||||
#else /* !__powerpc64__ */
|
||||
|
||||
enum { SIGNAL_FRAMESIZE = 64 };
|
||||
|
||||
#define PPC_LINUX_GET_REGS(CONTEXT) \
|
||||
({ \
|
||||
const unsigned char *pc = (CONTEXT)->ra; \
|
||||
struct gcc_regs *regs = NULL; \
|
||||
\
|
||||
/* li r0, 0x7777; sc (sigreturn old) */ \
|
||||
/* li r0, 0x0077; sc (sigreturn new) */ \
|
||||
/* li r0, 0x6666; sc (rt_sigreturn old) */ \
|
||||
/* li r0, 0x00AC; sc (rt_sigreturn new) */ \
|
||||
if (*(unsigned int *) (pc + 4) != 0x44000002) \
|
||||
; \
|
||||
else if (*(unsigned int *) (pc + 0) == 0x38007777 \
|
||||
|| *(unsigned int *) (pc + 0) == 0x38000077) \
|
||||
{ \
|
||||
struct sigframe { \
|
||||
char gap[SIGNAL_FRAMESIZE]; \
|
||||
unsigned long pad[7]; \
|
||||
struct gcc_regs *regs; \
|
||||
} *frame = (struct sigframe *) (CONTEXT)->cfa; \
|
||||
regs = frame->regs; \
|
||||
} \
|
||||
else if (*(unsigned int *) (pc + 0) == 0x38006666 \
|
||||
|| *(unsigned int *) (pc + 0) == 0x380000AC) \
|
||||
{ \
|
||||
struct rt_sigframe { \
|
||||
char gap[SIGNAL_FRAMESIZE + 16]; \
|
||||
char siginfo[128]; \
|
||||
struct gcc_ucontext uc; \
|
||||
} *frame = (struct rt_sigframe *) (CONTEXT)->cfa; \
|
||||
regs = frame->uc.regs; \
|
||||
} \
|
||||
regs; \
|
||||
})
|
||||
|
||||
#define LINUX_HWCAP_DEFAULT 0x80000000
|
||||
|
||||
#define PPC_LINUX_VREGS(REGS) &(REGS)->vregs
|
||||
|
||||
#endif
|
||||
|
||||
/* Do code reading to identify a signal frame, and set the frame
|
||||
state data appropriately. See unwind-dw2.c for the structs. */
|
||||
|
||||
#define MD_FALLBACK_FRAME_STATE_FOR(CONTEXT, FS, SUCCESS) \
|
||||
do { \
|
||||
static long hwcap = 0; \
|
||||
struct gcc_regs *regs = PPC_LINUX_GET_REGS (CONTEXT); \
|
||||
long new_cfa; \
|
||||
int i; \
|
||||
\
|
||||
if (regs == NULL) \
|
||||
break; \
|
||||
\
|
||||
new_cfa = regs->gpr[STACK_POINTER_REGNUM]; \
|
||||
(FS)->cfa_how = CFA_REG_OFFSET; \
|
||||
(FS)->cfa_reg = STACK_POINTER_REGNUM; \
|
||||
(FS)->cfa_offset = new_cfa - (long) (CONTEXT)->cfa; \
|
||||
\
|
||||
for (i = 0; i < 32; i++) \
|
||||
if (i != STACK_POINTER_REGNUM) \
|
||||
{ \
|
||||
(FS)->regs.reg[i].how = REG_SAVED_OFFSET; \
|
||||
(FS)->regs.reg[i].loc.offset \
|
||||
= (long) ®s->gpr[i] - new_cfa; \
|
||||
} \
|
||||
\
|
||||
(FS)->regs.reg[CR2_REGNO].how = REG_SAVED_OFFSET; \
|
||||
(FS)->regs.reg[CR2_REGNO].loc.offset \
|
||||
= (long) ®s->ccr - new_cfa; \
|
||||
\
|
||||
(FS)->regs.reg[LINK_REGISTER_REGNUM].how = REG_SAVED_OFFSET; \
|
||||
(FS)->regs.reg[LINK_REGISTER_REGNUM].loc.offset \
|
||||
= (long) ®s->link - new_cfa; \
|
||||
\
|
||||
(FS)->regs.reg[ARG_POINTER_REGNUM].how = REG_SAVED_OFFSET; \
|
||||
(FS)->regs.reg[ARG_POINTER_REGNUM].loc.offset \
|
||||
= (long) ®s->nip - new_cfa; \
|
||||
(FS)->retaddr_column = ARG_POINTER_REGNUM; \
|
||||
\
|
||||
if (hwcap == 0) \
|
||||
{ \
|
||||
/* __libc_stack_end holds the original stack passed to a \
|
||||
process. */ \
|
||||
extern long *__libc_stack_end; \
|
||||
long argc; \
|
||||
char **argv; \
|
||||
char **envp; \
|
||||
struct auxv \
|
||||
{ \
|
||||
long a_type; \
|
||||
long a_val; \
|
||||
} *auxp; \
|
||||
\
|
||||
/* The Linux kernel puts argc first on the stack. */ \
|
||||
argc = __libc_stack_end[0]; \
|
||||
/* Followed by argv, NULL terminated. */ \
|
||||
argv = (char **) __libc_stack_end + 1; \
|
||||
/* Followed by environment string pointers, NULL terminated. */ \
|
||||
envp = argv + argc + 1; \
|
||||
while (*envp++) \
|
||||
continue; \
|
||||
/* Followed by the aux vector, zero terminated. */ \
|
||||
for (auxp = (struct auxv *) envp; auxp->a_type != 0; ++auxp) \
|
||||
if (auxp->a_type == 16) \
|
||||
{ \
|
||||
hwcap = auxp->a_val; \
|
||||
break; \
|
||||
} \
|
||||
\
|
||||
/* These will already be set if we found AT_HWCAP. A non-zero \
|
||||
value stops us looking again if for some reason we couldn't \
|
||||
find AT_HWCAP. */ \
|
||||
hwcap |= LINUX_HWCAP_DEFAULT; \
|
||||
} \
|
||||
\
|
||||
/* If we have a FPU... */ \
|
||||
if (hwcap & 0x08000000) \
|
||||
for (i = 0; i < 32; i++) \
|
||||
{ \
|
||||
(FS)->regs.reg[i + 32].how = REG_SAVED_OFFSET; \
|
||||
(FS)->regs.reg[i + 32].loc.offset \
|
||||
= (long) ®s->fpr[i] - new_cfa; \
|
||||
} \
|
||||
\
|
||||
/* If we have a VMX unit... */ \
|
||||
if (hwcap & 0x10000000) \
|
||||
{ \
|
||||
struct gcc_vregs *vregs; \
|
||||
vregs = PPC_LINUX_VREGS (regs); \
|
||||
if (regs->msr & (1 << 25)) \
|
||||
{ \
|
||||
for (i = 0; i < 32; i++) \
|
||||
{ \
|
||||
(FS)->regs.reg[i + FIRST_ALTIVEC_REGNO].how \
|
||||
= REG_SAVED_OFFSET; \
|
||||
(FS)->regs.reg[i + FIRST_ALTIVEC_REGNO].loc.offset \
|
||||
= (long) &vregs[i] - new_cfa; \
|
||||
} \
|
||||
\
|
||||
(FS)->regs.reg[VSCR_REGNO].how = REG_SAVED_OFFSET; \
|
||||
(FS)->regs.reg[VSCR_REGNO].loc.offset \
|
||||
= (long) &vregs->vscr - new_cfa; \
|
||||
} \
|
||||
\
|
||||
(FS)->regs.reg[VRSAVE_REGNO].how = REG_SAVED_OFFSET; \
|
||||
(FS)->regs.reg[VRSAVE_REGNO].loc.offset \
|
||||
= (long) &vregs->vsave - new_cfa; \
|
||||
} \
|
||||
\
|
||||
goto SUCCESS; \
|
||||
} while (0)
|
@ -1,6 +1,6 @@
|
||||
/* Definitions of target machine for GNU compiler,
|
||||
for PowerPC machines running Linux.
|
||||
Copyright (C) 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003
|
||||
Copyright (C) 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004, 2005
|
||||
Free Software Foundation, Inc.
|
||||
Contributed by Michael Meissner (meissner@cygnus.com).
|
||||
|
||||
@ -24,6 +24,14 @@
|
||||
#undef MD_EXEC_PREFIX
|
||||
#undef MD_STARTFILE_PREFIX
|
||||
|
||||
/* Linux doesn't support saving and restoring 64-bit regs in a 32-bit
|
||||
process. */
|
||||
#define OS_MISSING_POWERPC64 1
|
||||
|
||||
/* glibc has float and long double forms of math functions. */
|
||||
#undef TARGET_C99_FUNCTIONS
|
||||
#define TARGET_C99_FUNCTIONS 1
|
||||
|
||||
#undef TARGET_OS_CPP_BUILTINS
|
||||
#define TARGET_OS_CPP_BUILTINS() \
|
||||
do \
|
||||
@ -86,94 +94,16 @@
|
||||
#undef TARGET_64BIT
|
||||
#define TARGET_64BIT 0
|
||||
|
||||
/* We don't need to generate entries in .fixup. */
|
||||
/* We don't need to generate entries in .fixup, except when
|
||||
-mrelocatable or -mrelocatable-lib is given. */
|
||||
#undef RELOCATABLE_NEEDS_FIXUP
|
||||
#define RELOCATABLE_NEEDS_FIXUP \
|
||||
(target_flags & target_flags_explicit & MASK_RELOCATABLE)
|
||||
|
||||
#define TARGET_ASM_FILE_END file_end_indicate_exec_stack
|
||||
|
||||
#define TARGET_HAS_F_SETLKW
|
||||
|
||||
/* Do code reading to identify a signal frame, and set the frame
|
||||
state data appropriately. See unwind-dw2.c for the structs. */
|
||||
|
||||
#ifdef IN_LIBGCC2
|
||||
#include <signal.h>
|
||||
|
||||
/* During the 2.5 kernel series the kernel ucontext was changed, but
|
||||
the new layout is compatible with the old one, so we just define
|
||||
and use the old one here for simplicity and compatibility. */
|
||||
|
||||
struct kernel_old_ucontext {
|
||||
unsigned long uc_flags;
|
||||
struct ucontext *uc_link;
|
||||
stack_t uc_stack;
|
||||
struct sigcontext_struct uc_mcontext;
|
||||
sigset_t uc_sigmask;
|
||||
};
|
||||
|
||||
enum { SIGNAL_FRAMESIZE = 64 };
|
||||
#include "config/rs6000/linux-unwind.h"
|
||||
#endif
|
||||
|
||||
#define MD_FALLBACK_FRAME_STATE_FOR(CONTEXT, FS, SUCCESS) \
|
||||
do { \
|
||||
unsigned char *pc_ = (CONTEXT)->ra; \
|
||||
struct sigcontext *sc_; \
|
||||
long new_cfa_; \
|
||||
int i_; \
|
||||
\
|
||||
/* li r0, 0x7777; sc (sigreturn old) */ \
|
||||
/* li r0, 0x0077; sc (sigreturn new) */ \
|
||||
/* li r0, 0x6666; sc (rt_sigreturn old) */ \
|
||||
/* li r0, 0x00AC; sc (rt_sigreturn new) */ \
|
||||
if (*(unsigned int *) (pc_+4) != 0x44000002) \
|
||||
break; \
|
||||
if (*(unsigned int *) (pc_+0) == 0x38007777 \
|
||||
|| *(unsigned int *) (pc_+0) == 0x38000077) \
|
||||
{ \
|
||||
struct sigframe { \
|
||||
char gap[SIGNAL_FRAMESIZE]; \
|
||||
struct sigcontext sigctx; \
|
||||
} *rt_ = (CONTEXT)->cfa; \
|
||||
sc_ = &rt_->sigctx; \
|
||||
} \
|
||||
else if (*(unsigned int *) (pc_+0) == 0x38006666 \
|
||||
|| *(unsigned int *) (pc_+0) == 0x380000AC) \
|
||||
{ \
|
||||
struct rt_sigframe { \
|
||||
char gap[SIGNAL_FRAMESIZE]; \
|
||||
unsigned long _unused[2]; \
|
||||
struct siginfo *pinfo; \
|
||||
void *puc; \
|
||||
struct siginfo info; \
|
||||
struct kernel_old_ucontext uc; \
|
||||
} *rt_ = (CONTEXT)->cfa; \
|
||||
sc_ = &rt_->uc.uc_mcontext; \
|
||||
} \
|
||||
else \
|
||||
break; \
|
||||
\
|
||||
new_cfa_ = sc_->regs->gpr[STACK_POINTER_REGNUM]; \
|
||||
(FS)->cfa_how = CFA_REG_OFFSET; \
|
||||
(FS)->cfa_reg = STACK_POINTER_REGNUM; \
|
||||
(FS)->cfa_offset = new_cfa_ - (long) (CONTEXT)->cfa; \
|
||||
\
|
||||
for (i_ = 0; i_ < 32; i_++) \
|
||||
if (i_ != STACK_POINTER_REGNUM) \
|
||||
{ \
|
||||
(FS)->regs.reg[i_].how = REG_SAVED_OFFSET; \
|
||||
(FS)->regs.reg[i_].loc.offset \
|
||||
= (long)&(sc_->regs->gpr[i_]) - new_cfa_; \
|
||||
} \
|
||||
\
|
||||
(FS)->regs.reg[LINK_REGISTER_REGNUM].how = REG_SAVED_OFFSET; \
|
||||
(FS)->regs.reg[LINK_REGISTER_REGNUM].loc.offset \
|
||||
= (long)&(sc_->regs->link) - new_cfa_; \
|
||||
\
|
||||
(FS)->regs.reg[CR0_REGNO].how = REG_SAVED_OFFSET; \
|
||||
(FS)->regs.reg[CR0_REGNO].loc.offset \
|
||||
= (long)&(sc_->regs->nip) - new_cfa_; \
|
||||
(FS)->retaddr_column = CR0_REGNO; \
|
||||
goto SUCCESS; \
|
||||
} while (0)
|
||||
|
||||
#define OS_MISSING_POWERPC64 1
|
||||
|
@ -1,6 +1,6 @@
|
||||
/* Definitions of target machine for GNU compiler,
|
||||
for 64 bit PowerPC linux.
|
||||
Copyright (C) 2000, 2001, 2002, 2003, 2004
|
||||
Copyright (C) 2000, 2001, 2002, 2003, 2004, 2005
|
||||
Free Software Foundation, Inc.
|
||||
|
||||
This file is part of GCC.
|
||||
@ -53,8 +53,11 @@
|
||||
#undef PROCESSOR_DEFAULT64
|
||||
#define PROCESSOR_DEFAULT64 PROCESSOR_PPC630
|
||||
|
||||
#undef TARGET_RELOCATABLE
|
||||
#define TARGET_RELOCATABLE (!TARGET_64BIT && (target_flags & MASK_RELOCATABLE))
|
||||
/* We don't need to generate entries in .fixup, except when
|
||||
-mrelocatable or -mrelocatable-lib is given. */
|
||||
#undef RELOCATABLE_NEEDS_FIXUP
|
||||
#define RELOCATABLE_NEEDS_FIXUP \
|
||||
(target_flags & target_flags_explicit & MASK_RELOCATABLE)
|
||||
|
||||
#undef RS6000_ABI_NAME
|
||||
#define RS6000_ABI_NAME (TARGET_64BIT ? "aixdesc" : "sysv")
|
||||
@ -188,6 +191,8 @@
|
||||
#define TARGET_EABI 0
|
||||
#undef TARGET_PROTOTYPE
|
||||
#define TARGET_PROTOTYPE 0
|
||||
#undef RELOCATABLE_NEEDS_FIXUP
|
||||
#define RELOCATABLE_NEEDS_FIXUP 0
|
||||
|
||||
#endif
|
||||
|
||||
@ -212,9 +217,6 @@
|
||||
#define PROFILE_HOOK(LABEL) \
|
||||
do { if (TARGET_64BIT) output_profile_hook (LABEL); } while (0)
|
||||
|
||||
/* We don't need to generate entries in .fixup. */
|
||||
#undef RELOCATABLE_NEEDS_FIXUP
|
||||
|
||||
/* PowerPC64 Linux word-aligns FP doubles when -malign-power is given. */
|
||||
#undef ADJUST_FIELD_ALIGN
|
||||
#define ADJUST_FIELD_ALIGN(FIELD, COMPUTED) \
|
||||
@ -287,6 +289,14 @@
|
||||
#undef MD_EXEC_PREFIX
|
||||
#undef MD_STARTFILE_PREFIX
|
||||
|
||||
/* Linux doesn't support saving and restoring 64-bit regs in a 32-bit
|
||||
process. */
|
||||
#define OS_MISSING_POWERPC64 !TARGET_64BIT
|
||||
|
||||
/* glibc has float and long double forms of math functions. */
|
||||
#undef TARGET_C99_FUNCTIONS
|
||||
#define TARGET_C99_FUNCTIONS 1
|
||||
|
||||
#undef TARGET_OS_CPP_BUILTINS
|
||||
#define TARGET_OS_CPP_BUILTINS() \
|
||||
do \
|
||||
@ -541,182 +551,13 @@ while (0)
|
||||
#undef DRAFT_V4_STRUCT_RET
|
||||
#define DRAFT_V4_STRUCT_RET (!TARGET_64BIT)
|
||||
|
||||
#define TARGET_ASM_FILE_END file_end_indicate_exec_stack
|
||||
#define TARGET_ASM_FILE_END rs6000_elf_end_indicate_exec_stack
|
||||
|
||||
#define TARGET_HAS_F_SETLKW
|
||||
|
||||
#define LINK_GCC_C_SEQUENCE_SPEC \
|
||||
"%{static:--start-group} %G %L %{static:--end-group}%{!static:%G}"
|
||||
|
||||
/* Do code reading to identify a signal frame, and set the frame
|
||||
state data appropriately. See unwind-dw2.c for the structs. */
|
||||
|
||||
#ifdef IN_LIBGCC2
|
||||
#include <signal.h>
|
||||
#ifdef __powerpc64__
|
||||
#include <sys/ucontext.h>
|
||||
|
||||
enum { SIGNAL_FRAMESIZE = 128 };
|
||||
|
||||
#else
|
||||
|
||||
/* During the 2.5 kernel series the kernel ucontext was changed, but
|
||||
the new layout is compatible with the old one, so we just define
|
||||
and use the old one here for simplicity and compatibility. */
|
||||
|
||||
struct kernel_old_ucontext {
|
||||
unsigned long uc_flags;
|
||||
struct ucontext *uc_link;
|
||||
stack_t uc_stack;
|
||||
struct sigcontext_struct uc_mcontext;
|
||||
sigset_t uc_sigmask;
|
||||
};
|
||||
enum { SIGNAL_FRAMESIZE = 64 };
|
||||
#include "config/rs6000/linux-unwind.h"
|
||||
#endif
|
||||
|
||||
#endif
|
||||
|
||||
#ifdef __powerpc64__
|
||||
|
||||
/* If the current unwind info (FS) does not contain explicit info
|
||||
saving R2, then we have to do a minor amount of code reading to
|
||||
figure out if it was saved. The big problem here is that the
|
||||
code that does the save/restore is generated by the linker, so
|
||||
we have no good way to determine at compile time what to do. */
|
||||
|
||||
#define MD_FROB_UPDATE_CONTEXT(CTX, FS) \
|
||||
do { \
|
||||
if ((FS)->regs.reg[2].how == REG_UNSAVED) \
|
||||
{ \
|
||||
unsigned int *insn \
|
||||
= (unsigned int *) \
|
||||
_Unwind_GetGR ((CTX), LINK_REGISTER_REGNUM); \
|
||||
if (*insn == 0xE8410028) \
|
||||
_Unwind_SetGRPtr ((CTX), 2, (CTX)->cfa + 40); \
|
||||
} \
|
||||
} while (0)
|
||||
|
||||
#define MD_FALLBACK_FRAME_STATE_FOR(CONTEXT, FS, SUCCESS) \
|
||||
do { \
|
||||
unsigned char *pc_ = (CONTEXT)->ra; \
|
||||
struct sigcontext *sc_; \
|
||||
long new_cfa_; \
|
||||
int i_; \
|
||||
\
|
||||
/* addi r1, r1, 128; li r0, 0x0077; sc (sigreturn) */ \
|
||||
/* addi r1, r1, 128; li r0, 0x00AC; sc (rt_sigreturn) */ \
|
||||
if (*(unsigned int *) (pc_+0) != 0x38210000 + SIGNAL_FRAMESIZE \
|
||||
|| *(unsigned int *) (pc_+8) != 0x44000002) \
|
||||
break; \
|
||||
if (*(unsigned int *) (pc_+4) == 0x38000077) \
|
||||
{ \
|
||||
struct sigframe { \
|
||||
char gap[SIGNAL_FRAMESIZE]; \
|
||||
struct sigcontext sigctx; \
|
||||
} *rt_ = (CONTEXT)->cfa; \
|
||||
sc_ = &rt_->sigctx; \
|
||||
} \
|
||||
else if (*(unsigned int *) (pc_+4) == 0x380000AC) \
|
||||
{ \
|
||||
struct rt_sigframe { \
|
||||
int tramp[6]; \
|
||||
struct siginfo *pinfo; \
|
||||
struct ucontext *puc; \
|
||||
} *rt_ = (struct rt_sigframe *) pc_; \
|
||||
sc_ = &rt_->puc->uc_mcontext; \
|
||||
} \
|
||||
else \
|
||||
break; \
|
||||
\
|
||||
new_cfa_ = sc_->regs->gpr[STACK_POINTER_REGNUM]; \
|
||||
(FS)->cfa_how = CFA_REG_OFFSET; \
|
||||
(FS)->cfa_reg = STACK_POINTER_REGNUM; \
|
||||
(FS)->cfa_offset = new_cfa_ - (long) (CONTEXT)->cfa; \
|
||||
\
|
||||
for (i_ = 0; i_ < 32; i_++) \
|
||||
if (i_ != STACK_POINTER_REGNUM) \
|
||||
{ \
|
||||
(FS)->regs.reg[i_].how = REG_SAVED_OFFSET; \
|
||||
(FS)->regs.reg[i_].loc.offset \
|
||||
= (long)&(sc_->regs->gpr[i_]) - new_cfa_; \
|
||||
} \
|
||||
\
|
||||
(FS)->regs.reg[LINK_REGISTER_REGNUM].how = REG_SAVED_OFFSET; \
|
||||
(FS)->regs.reg[LINK_REGISTER_REGNUM].loc.offset \
|
||||
= (long)&(sc_->regs->link) - new_cfa_; \
|
||||
\
|
||||
(FS)->regs.reg[ARG_POINTER_REGNUM].how = REG_SAVED_OFFSET; \
|
||||
(FS)->regs.reg[ARG_POINTER_REGNUM].loc.offset \
|
||||
= (long)&(sc_->regs->nip) - new_cfa_; \
|
||||
(FS)->retaddr_column = ARG_POINTER_REGNUM; \
|
||||
goto SUCCESS; \
|
||||
} while (0)
|
||||
|
||||
#else
|
||||
|
||||
#define MD_FALLBACK_FRAME_STATE_FOR(CONTEXT, FS, SUCCESS) \
|
||||
do { \
|
||||
unsigned char *pc_ = (CONTEXT)->ra; \
|
||||
struct sigcontext *sc_; \
|
||||
long new_cfa_; \
|
||||
int i_; \
|
||||
\
|
||||
/* li r0, 0x7777; sc (sigreturn old) */ \
|
||||
/* li r0, 0x0077; sc (sigreturn new) */ \
|
||||
/* li r0, 0x6666; sc (rt_sigreturn old) */ \
|
||||
/* li r0, 0x00AC; sc (rt_sigreturn new) */ \
|
||||
if (*(unsigned int *) (pc_+4) != 0x44000002) \
|
||||
break; \
|
||||
if (*(unsigned int *) (pc_+0) == 0x38007777 \
|
||||
|| *(unsigned int *) (pc_+0) == 0x38000077) \
|
||||
{ \
|
||||
struct sigframe { \
|
||||
char gap[SIGNAL_FRAMESIZE]; \
|
||||
struct sigcontext sigctx; \
|
||||
} *rt_ = (CONTEXT)->cfa; \
|
||||
sc_ = &rt_->sigctx; \
|
||||
} \
|
||||
else if (*(unsigned int *) (pc_+0) == 0x38006666 \
|
||||
|| *(unsigned int *) (pc_+0) == 0x380000AC) \
|
||||
{ \
|
||||
struct rt_sigframe { \
|
||||
char gap[SIGNAL_FRAMESIZE]; \
|
||||
unsigned long _unused[2]; \
|
||||
struct siginfo *pinfo; \
|
||||
void *puc; \
|
||||
struct siginfo info; \
|
||||
struct kernel_old_ucontext uc; \
|
||||
} *rt_ = (CONTEXT)->cfa; \
|
||||
sc_ = &rt_->uc.uc_mcontext; \
|
||||
} \
|
||||
else \
|
||||
break; \
|
||||
\
|
||||
new_cfa_ = sc_->regs->gpr[STACK_POINTER_REGNUM]; \
|
||||
(FS)->cfa_how = CFA_REG_OFFSET; \
|
||||
(FS)->cfa_reg = STACK_POINTER_REGNUM; \
|
||||
(FS)->cfa_offset = new_cfa_ - (long) (CONTEXT)->cfa; \
|
||||
\
|
||||
for (i_ = 0; i_ < 32; i_++) \
|
||||
if (i_ != STACK_POINTER_REGNUM) \
|
||||
{ \
|
||||
(FS)->regs.reg[i_].how = REG_SAVED_OFFSET; \
|
||||
(FS)->regs.reg[i_].loc.offset \
|
||||
= (long)&(sc_->regs->gpr[i_]) - new_cfa_; \
|
||||
} \
|
||||
\
|
||||
(FS)->regs.reg[LINK_REGISTER_REGNUM].how = REG_SAVED_OFFSET; \
|
||||
(FS)->regs.reg[LINK_REGISTER_REGNUM].loc.offset \
|
||||
= (long)&(sc_->regs->link) - new_cfa_; \
|
||||
\
|
||||
(FS)->regs.reg[CR0_REGNO].how = REG_SAVED_OFFSET; \
|
||||
(FS)->regs.reg[CR0_REGNO].loc.offset \
|
||||
= (long)&(sc_->regs->nip) - new_cfa_; \
|
||||
(FS)->retaddr_column = CR0_REGNO; \
|
||||
goto SUCCESS; \
|
||||
} while (0)
|
||||
|
||||
#endif
|
||||
|
||||
|
||||
#define OS_MISSING_POWERPC64 !TARGET_64BIT
|
||||
|
@ -62,13 +62,13 @@ rs6000_pragma_longcall (cpp_reader *pfile ATTRIBUTE_UNUSED)
|
||||
if (c_lex (&x) != CPP_CLOSE_PAREN)
|
||||
SYNTAX_ERROR ("missing close paren");
|
||||
|
||||
if (n != integer_zero_node && n != integer_one_node)
|
||||
if (!integer_zerop (n) && !integer_onep (n))
|
||||
SYNTAX_ERROR ("number must be 0 or 1");
|
||||
|
||||
if (c_lex (&x) != CPP_EOF)
|
||||
warning ("junk at end of #pragma longcall");
|
||||
|
||||
rs6000_default_long_calls = (n == integer_one_node);
|
||||
rs6000_default_long_calls = integer_onep (n);
|
||||
}
|
||||
|
||||
/* Handle defining many CPP flags based on TARGET_xxx. As a general
|
||||
@ -92,7 +92,15 @@ rs6000_cpu_cpp_builtins (cpp_reader *pfile)
|
||||
if (! TARGET_POWER && ! TARGET_POWER2 && ! TARGET_POWERPC)
|
||||
builtin_define ("_ARCH_COM");
|
||||
if (TARGET_ALTIVEC)
|
||||
builtin_define ("__ALTIVEC__");
|
||||
{
|
||||
builtin_define ("__ALTIVEC__");
|
||||
builtin_define ("__VEC__=10206");
|
||||
|
||||
/* Define the AltiVec syntactic elements. */
|
||||
builtin_define ("__vector=__attribute__((altivec(vector__)))");
|
||||
builtin_define ("__pixel=__attribute__((altivec(pixel__))) unsigned short");
|
||||
builtin_define ("__bool=__attribute__((altivec(bool__))) unsigned");
|
||||
}
|
||||
if (TARGET_SPE)
|
||||
builtin_define ("__SPE__");
|
||||
if (TARGET_SOFT_FLOAT)
|
||||
|
@ -116,7 +116,7 @@ extern enum rtx_code rs6000_reverse_condition (enum machine_mode,
|
||||
extern void rs6000_emit_sCOND (enum rtx_code, rtx);
|
||||
extern void rs6000_emit_cbranch (enum rtx_code, rtx);
|
||||
extern char * output_cbranch (rtx, const char *, int, rtx);
|
||||
extern char * output_e500_flip_gt_bit (rtx, rtx);
|
||||
extern char * output_e500_flip_eq_bit (rtx, rtx);
|
||||
extern rtx rs6000_emit_set_const (rtx, enum machine_mode, rtx, int);
|
||||
extern int rs6000_emit_cmove (rtx, rtx, rtx, rtx);
|
||||
extern void rs6000_emit_minmax (rtx, enum rtx_code, rtx, rtx);
|
||||
|
File diff suppressed because it is too large
Load Diff
@ -258,7 +258,7 @@ extern int target_flags;
|
||||
#define TARGET_POWERPC64 (target_flags & MASK_POWERPC64)
|
||||
#endif
|
||||
|
||||
#define TARGET_XL_CALL 0
|
||||
#define TARGET_XL_COMPAT 0
|
||||
|
||||
/* Run-time compilation parameters selecting different hardware subsets.
|
||||
|
||||
@ -464,6 +464,9 @@ enum group_termination
|
||||
{"longcall", &rs6000_longcall_switch, \
|
||||
N_("Avoid all range limits on call instructions"), 0}, \
|
||||
{"no-longcall", &rs6000_longcall_switch, "", 0}, \
|
||||
{"warn-altivec-long", &rs6000_warn_altivec_long_switch, \
|
||||
N_("Warn about deprecated 'vector long ...' AltiVec type usage"), 0}, \
|
||||
{"no-warn-altivec-long", &rs6000_warn_altivec_long_switch, "", 0}, \
|
||||
{"sched-costly-dep=", &rs6000_sched_costly_dep_str, \
|
||||
N_("Determine which dependences between insns are considered costly"), 0}, \
|
||||
{"insert-sched-nops=", &rs6000_sched_insert_nops_str, \
|
||||
@ -532,6 +535,9 @@ extern enum rs6000_dependence_cost rs6000_sched_costly_dep;
|
||||
extern const char *rs6000_sched_insert_nops_str;
|
||||
extern enum rs6000_nop_insertion rs6000_sched_insert_nops;
|
||||
|
||||
extern int rs6000_warn_altivec_long;
|
||||
extern const char *rs6000_warn_altivec_long_switch;
|
||||
|
||||
/* Alignment options for fields in structures for sub-targets following
|
||||
AIX-like ABI.
|
||||
ALIGN_POWER word-aligns FP doubles (default AIX ABI).
|
||||
@ -1165,6 +1171,9 @@ extern enum rs6000_nop_insertion rs6000_sched_insert_nops;
|
||||
= fixed_regs[RS6000_PIC_OFFSET_TABLE_REGNUM] \
|
||||
= call_used_regs[RS6000_PIC_OFFSET_TABLE_REGNUM] \
|
||||
= call_really_used_regs[RS6000_PIC_OFFSET_TABLE_REGNUM] = 1; \
|
||||
if (TARGET_TOC && TARGET_MINIMAL_TOC) \
|
||||
fixed_regs[RS6000_PIC_OFFSET_TABLE_REGNUM] \
|
||||
= call_used_regs[RS6000_PIC_OFFSET_TABLE_REGNUM] = 1; \
|
||||
if (TARGET_ALTIVEC) \
|
||||
global_regs[VSCR_REGNO] = 1; \
|
||||
if (TARGET_SPE) \
|
||||
@ -2918,9 +2927,10 @@ enum rs6000_builtins
|
||||
ALTIVEC_BUILTIN_ABS_V4SI,
|
||||
ALTIVEC_BUILTIN_ABS_V4SF,
|
||||
ALTIVEC_BUILTIN_ABS_V8HI,
|
||||
ALTIVEC_BUILTIN_ABS_V16QI
|
||||
ALTIVEC_BUILTIN_ABS_V16QI,
|
||||
ALTIVEC_BUILTIN_COMPILETIME_ERROR,
|
||||
/* SPE builtins. */
|
||||
, SPE_BUILTIN_EVADDW,
|
||||
SPE_BUILTIN_EVADDW,
|
||||
SPE_BUILTIN_EVAND,
|
||||
SPE_BUILTIN_EVANDC,
|
||||
SPE_BUILTIN_EVDIVWS,
|
||||
|
@ -1,6 +1,6 @@
|
||||
;; Machine description for IBM RISC System 6000 (POWER) for GNU C compiler
|
||||
;; Copyright (C) 1990, 1991, 1992, 1993, 1994, 1995, 1996, 1997, 1998,
|
||||
;; 1999, 2000, 2001, 2002, 2003, 2004 Free Software Foundation, Inc.
|
||||
;; 1999, 2000, 2001, 2002, 2003, 2004, 2005 Free Software Foundation, Inc.
|
||||
;; Contributed by Richard Kenner (kenner@vlsi1.ultra.nyu.edu)
|
||||
|
||||
;; This file is part of GCC.
|
||||
@ -50,7 +50,7 @@
|
||||
(UNSPEC_TLSGOTTPREL 28)
|
||||
(UNSPEC_TLSTLS 29)
|
||||
(UNSPEC_FIX_TRUNC_TF 30) ; fadd, rounding towards zero
|
||||
(UNSPEC_MV_CR_GT 31) ; move_from_CR_gt_bit
|
||||
(UNSPEC_MV_CR_EQ 31) ; move_from_CR_eq_bit
|
||||
])
|
||||
|
||||
;;
|
||||
@ -2404,61 +2404,6 @@
|
||||
}"
|
||||
[(set_attr "length" "8")])
|
||||
|
||||
(define_insn_and_split "*andsi3_internal7"
|
||||
[(set (match_operand:CC 2 "cc_reg_operand" "=x,?y")
|
||||
(compare:CC (and:SI (match_operand:SI 0 "gpc_reg_operand" "r,r")
|
||||
(match_operand:SI 1 "mask_operand_wrap" "i,i"))
|
||||
(const_int 0)))
|
||||
(clobber (match_scratch:SI 3 "=r,r"))]
|
||||
"TARGET_POWERPC64"
|
||||
"#"
|
||||
"TARGET_POWERPC64"
|
||||
[(parallel [(set (match_dup 2)
|
||||
(compare:CC (and:SI (rotate:SI (match_dup 0) (match_dup 4))
|
||||
(match_dup 5))
|
||||
(const_int 0)))
|
||||
(clobber (match_dup 3))])]
|
||||
"
|
||||
{
|
||||
int mb = extract_MB (operands[1]);
|
||||
int me = extract_ME (operands[1]);
|
||||
operands[4] = GEN_INT (me + 1);
|
||||
operands[5] = GEN_INT (~((HOST_WIDE_INT) -1 << (33 + me - mb)));
|
||||
}"
|
||||
[(set_attr "type" "delayed_compare,compare")
|
||||
(set_attr "length" "4,8")])
|
||||
|
||||
(define_insn_and_split "*andsi3_internal8"
|
||||
[(set (match_operand:CC 3 "cc_reg_operand" "=x,??y")
|
||||
(compare:CC (and:SI (match_operand:SI 1 "gpc_reg_operand" "r,r")
|
||||
(match_operand:SI 2 "mask_operand_wrap" "i,i"))
|
||||
(const_int 0)))
|
||||
(set (match_operand:SI 0 "gpc_reg_operand" "=r,r")
|
||||
(and:SI (match_dup 1)
|
||||
(match_dup 2)))]
|
||||
"TARGET_POWERPC64"
|
||||
"#"
|
||||
"TARGET_POWERPC64"
|
||||
[(parallel [(set (match_dup 3)
|
||||
(compare:CC (and:SI (rotate:SI (match_dup 1) (match_dup 4))
|
||||
(match_dup 5))
|
||||
(const_int 0)))
|
||||
(set (match_dup 0)
|
||||
(and:SI (rotate:SI (match_dup 1) (match_dup 4))
|
||||
(match_dup 5)))])
|
||||
(set (match_dup 0)
|
||||
(rotate:SI (match_dup 0) (match_dup 6)))]
|
||||
"
|
||||
{
|
||||
int mb = extract_MB (operands[2]);
|
||||
int me = extract_ME (operands[2]);
|
||||
operands[4] = GEN_INT (me + 1);
|
||||
operands[6] = GEN_INT (32 - (me + 1));
|
||||
operands[5] = GEN_INT (~((HOST_WIDE_INT) -1 << (33 + me - mb)));
|
||||
}"
|
||||
[(set_attr "type" "delayed_compare,compare")
|
||||
(set_attr "length" "8,12")])
|
||||
|
||||
(define_expand "iorsi3"
|
||||
[(set (match_operand:SI 0 "gpc_reg_operand" "")
|
||||
(ior:SI (match_operand:SI 1 "gpc_reg_operand" "")
|
||||
@ -5245,16 +5190,18 @@
|
||||
(define_expand "floatdisf2"
|
||||
[(set (match_operand:SF 0 "gpc_reg_operand" "")
|
||||
(float:SF (match_operand:DI 1 "gpc_reg_operand" "")))]
|
||||
"TARGET_64BIT && TARGET_HARD_FLOAT && TARGET_FPRS"
|
||||
"TARGET_POWERPC64 && TARGET_HARD_FLOAT && TARGET_FPRS"
|
||||
"
|
||||
{
|
||||
rtx val = operands[1];
|
||||
if (!flag_unsafe_math_optimizations)
|
||||
{
|
||||
rtx label = gen_label_rtx ();
|
||||
emit_insn (gen_floatdisf2_internal2 (operands[1], label));
|
||||
val = gen_reg_rtx (DImode);
|
||||
emit_insn (gen_floatdisf2_internal2 (val, operands[1], label));
|
||||
emit_label (label);
|
||||
}
|
||||
emit_insn (gen_floatdisf2_internal1 (operands[0], operands[1]));
|
||||
emit_insn (gen_floatdisf2_internal1 (operands[0], val));
|
||||
DONE;
|
||||
}")
|
||||
|
||||
@ -5279,30 +5226,31 @@
|
||||
;; by a bit that won't be lost at that stage, but is below the SFmode
|
||||
;; rounding position.
|
||||
(define_expand "floatdisf2_internal2"
|
||||
[(parallel [(set (match_dup 4)
|
||||
(compare:CC (and:DI (match_operand:DI 0 "" "")
|
||||
(const_int 2047))
|
||||
(const_int 0)))
|
||||
(set (match_dup 2) (and:DI (match_dup 0) (const_int 2047)))
|
||||
(clobber (match_scratch:CC 7 ""))])
|
||||
(set (match_dup 3) (ashiftrt:DI (match_dup 0) (const_int 53)))
|
||||
(set (match_dup 3) (plus:DI (match_dup 3) (const_int 1)))
|
||||
(set (pc) (if_then_else (eq (match_dup 4) (const_int 0))
|
||||
(label_ref (match_operand:DI 1 "" ""))
|
||||
[(set (match_dup 3) (ashiftrt:DI (match_operand:DI 1 "" "")
|
||||
(const_int 53)))
|
||||
(parallel [(set (match_operand:DI 0 "" "") (and:DI (match_dup 1)
|
||||
(const_int 2047)))
|
||||
(clobber (scratch:CC))])
|
||||
(set (match_dup 3) (plus:DI (match_dup 3)
|
||||
(const_int 1)))
|
||||
(set (match_dup 0) (plus:DI (match_dup 0)
|
||||
(const_int 2047)))
|
||||
(set (match_dup 4) (compare:CCUNS (match_dup 3)
|
||||
(const_int 3)))
|
||||
(set (match_dup 0) (ior:DI (match_dup 0)
|
||||
(match_dup 1)))
|
||||
(parallel [(set (match_dup 0) (and:DI (match_dup 0)
|
||||
(const_int -2048)))
|
||||
(clobber (scratch:CC))])
|
||||
(set (pc) (if_then_else (geu (match_dup 4) (const_int 0))
|
||||
(label_ref (match_operand:DI 2 "" ""))
|
||||
(pc)))
|
||||
(set (match_dup 5) (compare:CCUNS (match_dup 3) (const_int 2)))
|
||||
(set (pc) (if_then_else (ltu (match_dup 5) (const_int 0))
|
||||
(label_ref (match_dup 1))
|
||||
(pc)))
|
||||
(set (match_dup 0) (xor:DI (match_dup 0) (match_dup 2)))
|
||||
(set (match_dup 0) (ior:DI (match_dup 0) (const_int 2048)))]
|
||||
"TARGET_64BIT && TARGET_HARD_FLOAT && TARGET_FPRS"
|
||||
(set (match_dup 0) (match_dup 1))]
|
||||
"TARGET_POWERPC64 && TARGET_HARD_FLOAT && TARGET_FPRS"
|
||||
"
|
||||
{
|
||||
operands[2] = gen_reg_rtx (DImode);
|
||||
operands[3] = gen_reg_rtx (DImode);
|
||||
operands[4] = gen_reg_rtx (CCmode);
|
||||
operands[5] = gen_reg_rtx (CCUNSmode);
|
||||
operands[4] = gen_reg_rtx (CCUNSmode);
|
||||
}")
|
||||
|
||||
;; Define the DImode operations that can be done in a small number
|
||||
@ -8311,14 +8259,36 @@
|
||||
DONE;
|
||||
})
|
||||
|
||||
(define_insn "trunctfdf2"
|
||||
[(set (match_operand:DF 0 "gpc_reg_operand" "=f")
|
||||
(float_truncate:DF (match_operand:TF 1 "gpc_reg_operand" "f")))]
|
||||
(define_expand "trunctfdf2"
|
||||
[(set (match_operand:DF 0 "gpc_reg_operand" "")
|
||||
(float_truncate:DF (match_operand:TF 1 "gpc_reg_operand" "")))]
|
||||
"(DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_DARWIN)
|
||||
&& TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_LONG_DOUBLE_128"
|
||||
"")
|
||||
|
||||
(define_insn_and_split "trunctfdf2_internal1"
|
||||
[(set (match_operand:DF 0 "gpc_reg_operand" "=f,?f")
|
||||
(float_truncate:DF (match_operand:TF 1 "gpc_reg_operand" "0,f")))]
|
||||
"(DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_DARWIN) && !TARGET_XL_COMPAT
|
||||
&& TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_LONG_DOUBLE_128"
|
||||
"@
|
||||
#
|
||||
fmr %0,%1"
|
||||
"&& reload_completed && REGNO (operands[0]) == REGNO (operands[1])"
|
||||
[(const_int 0)]
|
||||
{
|
||||
emit_note (NOTE_INSN_DELETED);
|
||||
DONE;
|
||||
}
|
||||
[(set_attr "type" "fp")])
|
||||
|
||||
(define_insn "trunctfdf2_internal2"
|
||||
[(set (match_operand:DF 0 "gpc_reg_operand" "=f")
|
||||
(float_truncate:DF (match_operand:TF 1 "gpc_reg_operand" "f")))]
|
||||
"(DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_DARWIN) && TARGET_XL_COMPAT
|
||||
&& TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_LONG_DOUBLE_128"
|
||||
"fadd %0,%1,%L1"
|
||||
[(set_attr "type" "fp")
|
||||
(set_attr "length" "4")])
|
||||
[(set_attr "type" "fp")])
|
||||
|
||||
(define_insn_and_split "trunctfsf2"
|
||||
[(set (match_operand:SF 0 "gpc_reg_operand" "=f")
|
||||
@ -10081,11 +10051,10 @@
|
||||
|
||||
(define_insn "load_toc_v4_PIC_1b"
|
||||
[(set (match_operand:SI 0 "register_operand" "=l")
|
||||
(match_operand:SI 1 "immediate_operand" "s"))
|
||||
(use (unspec [(match_dup 1) (match_operand 2 "immediate_operand" "s")]
|
||||
(unspec:SI [(match_operand:SI 1 "immediate_operand" "s")]
|
||||
UNSPEC_TOCPTR))]
|
||||
"TARGET_ELF && DEFAULT_ABI != ABI_AIX && flag_pic == 2"
|
||||
"bcl 20,31,%1+4\\n%1:\\n\\t.long %2-%1"
|
||||
"bcl 20,31,$+8\\n\\t.long %1-$"
|
||||
[(set_attr "type" "branch")
|
||||
(set_attr "length" "8")])
|
||||
|
||||
@ -11349,11 +11318,72 @@
|
||||
[(set (match_operand:CCFP 0 "cc_reg_operand" "=y")
|
||||
(compare:CCFP (match_operand:TF 1 "gpc_reg_operand" "f")
|
||||
(match_operand:TF 2 "gpc_reg_operand" "f")))]
|
||||
"(DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_DARWIN)
|
||||
"(DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_DARWIN) && !TARGET_XL_COMPAT
|
||||
&& TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_LONG_DOUBLE_128"
|
||||
"fcmpu %0,%1,%2\;bne %0,$+8\;fcmpu %0,%L1,%L2"
|
||||
[(set_attr "type" "fpcompare")
|
||||
(set_attr "length" "12")])
|
||||
|
||||
(define_insn_and_split "*cmptf_internal2"
|
||||
[(set (match_operand:CCFP 0 "cc_reg_operand" "=y")
|
||||
(compare:CCFP (match_operand:TF 1 "gpc_reg_operand" "f")
|
||||
(match_operand:TF 2 "gpc_reg_operand" "f")))
|
||||
(clobber (match_scratch:DF 3 "=f"))
|
||||
(clobber (match_scratch:DF 4 "=f"))
|
||||
(clobber (match_scratch:DF 5 "=f"))
|
||||
(clobber (match_scratch:DF 6 "=f"))
|
||||
(clobber (match_scratch:DF 7 "=f"))
|
||||
(clobber (match_scratch:DF 8 "=f"))
|
||||
(clobber (match_scratch:DF 9 "=f"))
|
||||
(clobber (match_scratch:DF 10 "=f"))]
|
||||
"(DEFAULT_ABI == ABI_AIX || DEFAULT_ABI == ABI_DARWIN) && TARGET_XL_COMPAT
|
||||
&& TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_LONG_DOUBLE_128"
|
||||
"#"
|
||||
"&& reload_completed"
|
||||
[(set (match_dup 3) (match_dup 13))
|
||||
(set (match_dup 4) (match_dup 14))
|
||||
(set (match_dup 9) (abs:DF (match_dup 5)))
|
||||
(set (match_dup 0) (compare:CCFP (match_dup 9) (match_dup 3)))
|
||||
(set (pc) (if_then_else (ne (match_dup 0) (const_int 0))
|
||||
(label_ref (match_dup 11))
|
||||
(pc)))
|
||||
(set (match_dup 0) (compare:CCFP (match_dup 5) (match_dup 7)))
|
||||
(set (pc) (label_ref (match_dup 12)))
|
||||
(match_dup 11)
|
||||
(set (match_dup 10) (minus:DF (match_dup 5) (match_dup 7)))
|
||||
(set (match_dup 9) (minus:DF (match_dup 6) (match_dup 8)))
|
||||
(set (match_dup 9) (plus:DF (match_dup 10) (match_dup 9)))
|
||||
(set (match_dup 0) (compare:CCFP (match_dup 7) (match_dup 4)))
|
||||
(match_dup 12)]
|
||||
{
|
||||
REAL_VALUE_TYPE rv;
|
||||
const int lo_word = FLOAT_WORDS_BIG_ENDIAN ? GET_MODE_SIZE (DFmode) : 0;
|
||||
const int hi_word = FLOAT_WORDS_BIG_ENDIAN ? 0 : GET_MODE_SIZE (DFmode);
|
||||
|
||||
operands[5] = simplify_gen_subreg (DFmode, operands[1], TFmode, hi_word);
|
||||
operands[6] = simplify_gen_subreg (DFmode, operands[1], TFmode, lo_word);
|
||||
operands[7] = simplify_gen_subreg (DFmode, operands[2], TFmode, hi_word);
|
||||
operands[8] = simplify_gen_subreg (DFmode, operands[2], TFmode, lo_word);
|
||||
operands[11] = gen_label_rtx ();
|
||||
operands[12] = gen_label_rtx ();
|
||||
real_inf (&rv);
|
||||
operands[13] = force_const_mem (DFmode,
|
||||
CONST_DOUBLE_FROM_REAL_VALUE (rv, DFmode));
|
||||
operands[14] = force_const_mem (DFmode,
|
||||
CONST_DOUBLE_FROM_REAL_VALUE (dconst0,
|
||||
DFmode));
|
||||
if (TARGET_TOC)
|
||||
{
|
||||
operands[13] = gen_rtx_MEM (DFmode,
|
||||
create_TOC_reference (XEXP (operands[13], 0)));
|
||||
operands[14] = gen_rtx_MEM (DFmode,
|
||||
create_TOC_reference (XEXP (operands[14], 0)));
|
||||
set_mem_alias_set (operands[13], get_TOC_alias_set ());
|
||||
set_mem_alias_set (operands[14], get_TOC_alias_set ());
|
||||
RTX_UNCHANGING_P (operands[13]) = 1;
|
||||
RTX_UNCHANGING_P (operands[14]) = 1;
|
||||
}
|
||||
})
|
||||
|
||||
;; Now we have the scc insns. We can do some combinations because of the
|
||||
;; way the machine works.
|
||||
@ -11376,10 +11406,10 @@
|
||||
(const_string "mfcr")))
|
||||
(set_attr "length" "12")])
|
||||
|
||||
;; Same as above, but get the GT bit.
|
||||
(define_insn "move_from_CR_gt_bit"
|
||||
;; Same as above, but get the EQ bit.
|
||||
(define_insn "move_from_CR_eq_bit"
|
||||
[(set (match_operand:SI 0 "gpc_reg_operand" "=r")
|
||||
(unspec:SI [(match_operand 1 "cc_reg_operand" "y")] UNSPEC_MV_CR_GT))]
|
||||
(unspec:SI [(match_operand 1 "cc_reg_operand" "y")] UNSPEC_MV_CR_EQ))]
|
||||
"TARGET_E500"
|
||||
"mfcr %0\;{rlinm|rlwinm} %0,%0,%D1,1"
|
||||
[(set_attr "type" "mfcr")
|
||||
|
@ -1,5 +1,6 @@
|
||||
/* Definitions for rtems targeting a PowerPC using elf.
|
||||
Copyright (C) 1996, 1997, 2000, 2001, 2002, 2003 Free Software Foundation, Inc.
|
||||
Copyright (C) 1996, 1997, 2000, 2001, 2002, 2003, 2005
|
||||
Free Software Foundation, Inc.
|
||||
Contributed by Joel Sherrill (joel@OARcorp.com).
|
||||
|
||||
This file is part of GCC.
|
||||
@ -27,6 +28,7 @@
|
||||
{ \
|
||||
builtin_define_std ("PPC"); \
|
||||
builtin_define ("__rtems__"); \
|
||||
builtin_define ("__USE_INIT_FINI__"); \
|
||||
builtin_assert ("system=rtems"); \
|
||||
builtin_assert ("cpu=powerpc"); \
|
||||
builtin_assert ("machine=powerpc"); \
|
||||
@ -36,3 +38,20 @@
|
||||
|
||||
#undef CPP_OS_DEFAULT_SPEC
|
||||
#define CPP_OS_DEFAULT_SPEC "%(cpp_os_rtems)"
|
||||
|
||||
#define CPP_OS_RTEMS_SPEC "\
|
||||
%{!mcpu*: %{!Dppc*: %{!Dmpc*: -Dmpc750} } }\
|
||||
%{mcpu=403: %{!Dppc*: %{!Dmpc*: -Dppc403} } } \
|
||||
%{mcpu=505: %{!Dppc*: %{!Dmpc*: -Dmpc505} } } \
|
||||
%{mcpu=601: %{!Dppc*: %{!Dmpc*: -Dppc601} } } \
|
||||
%{mcpu=602: %{!Dppc*: %{!Dmpc*: -Dppc602} } } \
|
||||
%{mcpu=603: %{!Dppc*: %{!Dmpc*: -Dppc603} } } \
|
||||
%{mcpu=603e: %{!Dppc*: %{!Dmpc*: -Dppc603e} } } \
|
||||
%{mcpu=604: %{!Dppc*: %{!Dmpc*: -Dmpc604} } } \
|
||||
%{mcpu=750: %{!Dppc*: %{!Dmpc*: -Dmpc750} } } \
|
||||
%{mcpu=821: %{!Dppc*: %{!Dmpc*: -Dmpc821} } } \
|
||||
%{mcpu=860: %{!Dppc*: %{!Dmpc*: -Dmpc860} } }"
|
||||
|
||||
#undef SUBSUBTARGET_EXTRA_SPECS
|
||||
#define SUBSUBTARGET_EXTRA_SPECS \
|
||||
{ "cpp_os_rtems", CPP_OS_RTEMS_SPEC }
|
||||
|
@ -1088,4 +1088,23 @@ __ev_set_spefscr_frmc (int rnd)
|
||||
__builtin_spe_mtspefscr (i);
|
||||
}
|
||||
|
||||
/* The SPE PIM says these are declared in <spe.h>, although they are
|
||||
not provided by GCC: they must be taken from a separate
|
||||
library. */
|
||||
extern short int atosfix16 (const char *);
|
||||
extern int atosfix32 (const char *);
|
||||
extern long long atosfix64 (const char *);
|
||||
|
||||
extern unsigned short atoufix16 (const char *);
|
||||
extern unsigned int atoufix32 (const char *);
|
||||
extern unsigned long long atoufix64 (const char *);
|
||||
|
||||
extern short int strtosfix16 (const char *, char **);
|
||||
extern int strtosfix32 (const char *, char **);
|
||||
extern long long strtosfix64 (const char *, char **);
|
||||
|
||||
extern unsigned short int strtoufix16 (const char *, char **);
|
||||
extern unsigned int strtoufix32 (const char *, char **);
|
||||
extern unsigned long long strtoufix64 (const char *, char **);
|
||||
|
||||
#endif /* _SPE_H */
|
||||
|
@ -2458,14 +2458,14 @@
|
||||
;; FP comparison stuff.
|
||||
|
||||
;; Flip the GT bit.
|
||||
(define_insn "e500_flip_gt_bit"
|
||||
(define_insn "e500_flip_eq_bit"
|
||||
[(set (match_operand:CCFP 0 "cc_reg_operand" "=y")
|
||||
(unspec:CCFP
|
||||
[(match_operand:CCFP 1 "cc_reg_operand" "y")] 999))]
|
||||
"!TARGET_FPRS && TARGET_HARD_FLOAT"
|
||||
"*
|
||||
{
|
||||
return output_e500_flip_gt_bit (operands[0], operands[1]);
|
||||
return output_e500_flip_eq_bit (operands[0], operands[1]);
|
||||
}"
|
||||
[(set_attr "type" "cr_logical")])
|
||||
|
||||
|
@ -1086,7 +1086,7 @@ extern int fixuplabelno;
|
||||
#define LINK_START_FREEBSD_SPEC ""
|
||||
|
||||
#define LINK_OS_FREEBSD_SPEC "\
|
||||
%{p:%e`-p' not supported; use `-pg' and gprof(1)} \
|
||||
%{p:%nconsider using `-pg' instead of `-p' with gprof(1)} \
|
||||
%{Wl,*:%*} \
|
||||
%{v:-V} \
|
||||
%{assert*} %{R*} %{rpath*} %{defsym*} \
|
||||
@ -1115,8 +1115,9 @@ extern int fixuplabelno;
|
||||
%{static:crtbeginT.o%s;shared|pie:crtbeginS.o%s;:crtbegin.o%s}"
|
||||
#endif
|
||||
|
||||
#define ENDFILE_LINUX_SPEC "%{!shared:crtend.o%s} %{shared:crtendS.o%s} \
|
||||
%{mnewlib: ecrtn.o%s} %{!mnewlib: crtn.o%s}"
|
||||
#define ENDFILE_LINUX_SPEC "\
|
||||
%{shared|pie:crtendS.o%s;:crtend.o%s} \
|
||||
%{mnewlib:ecrtn.o%s;:crtn.o%s}"
|
||||
|
||||
#define LINK_START_LINUX_SPEC ""
|
||||
|
||||
@ -1358,4 +1359,4 @@ ncrtn.o%s"
|
||||
#define DOUBLE_INT_ASM_OP "\t.quad\t"
|
||||
|
||||
/* Generate entries in .fixup for relocatable addresses. */
|
||||
#define RELOCATABLE_NEEDS_FIXUP
|
||||
#define RELOCATABLE_NEEDS_FIXUP 1
|
||||
|
@ -58,9 +58,12 @@ SHLIB_LINK = $(GCC_FOR_TARGET) $(LIBGCC2_CFLAGS) -shared -nodefaultlibs \
|
||||
SHLIB_INSTALL = $(INSTALL_DATA) @shlib_base_name@.a $$(DESTDIR)$$(slibdir)/
|
||||
SHLIB_LIBS = -lc `case @shlib_base_name@ in *pthread*) echo -lpthread ;; esac`
|
||||
SHLIB_MKMAP = $(srcdir)/mkmap-flat.awk
|
||||
SHLIB_MAPFILES = $(srcdir)/libgcc-std.ver
|
||||
SHLIB_MAPFILES = $(srcdir)/libgcc-std.ver $(srcdir)/config/rs6000/libgcc-ppc64.ver
|
||||
SHLIB_NM_FLAGS = -Bpg -X32_64
|
||||
|
||||
# GCC 128-bit long double support routines.
|
||||
LIB2FUNCS_EXTRA = $(srcdir)/config/rs6000/darwin-ldouble.c
|
||||
|
||||
# Either 32-bit and 64-bit objects in archives.
|
||||
AR_FLAGS_FOR_TARGET = -X32_64
|
||||
|
||||
|
@ -39,9 +39,12 @@ SHLIB_LINK = $(GCC_FOR_TARGET) $(LIBGCC2_CFLAGS) -shared -nodefaultlibs \
|
||||
SHLIB_INSTALL = $(INSTALL_DATA) @shlib_base_name@.a $$(DESTDIR)$$(slibdir)/
|
||||
SHLIB_LIBS = -lc `case @shlib_base_name@ in *pthread*) echo -lpthread ;; esac`
|
||||
SHLIB_MKMAP = $(srcdir)/mkmap-flat.awk
|
||||
SHLIB_MAPFILES = $(srcdir)/libgcc-std.ver
|
||||
SHLIB_MAPFILES = $(srcdir)/libgcc-std.ver $(srcdir)/config/rs6000/libgcc-ppc64.ver
|
||||
SHLIB_NM_FLAGS = -Bpg -X32_64
|
||||
|
||||
# GCC 128-bit long double support routines.
|
||||
LIB2FUNCS_EXTRA = $(srcdir)/config/rs6000/darwin-ldouble.c
|
||||
|
||||
# Either 32-bit and 64-bit objects in archives.
|
||||
AR_FLAGS_FOR_TARGET = -X32_64
|
||||
|
||||
|
@ -1,8 +1,9 @@
|
||||
|
||||
#rs6000/t-linux64
|
||||
|
||||
LIB2FUNCS_EXTRA = tramp.S $(srcdir)/config/rs6000/ppc64-fp.c \
|
||||
$(srcdir)/config/rs6000/darwin-ldouble.c
|
||||
LIB2FUNCS_EXTRA = tramp.S $(srcdir)/config/rs6000/ppc64-fp.c
|
||||
LIB2FUNCS_STATIC_EXTRA = eabi.S $(srcdir)/config/rs6000/darwin-ldouble.c
|
||||
LIB2FUNCS_SHARED_EXTRA = $(srcdir)/config/rs6000/darwin-ldouble-shared.c
|
||||
|
||||
TARGET_LIBGCC2_CFLAGS = -mno-minimal-toc -fPIC -specs=bispecs
|
||||
|
||||
|
@ -27,6 +27,9 @@ MULTILIB_MATCHES = $(MULTILIB_MATCHES_FLOAT) \
|
||||
mcpu?powerpc=mpowerpc-gpopt \
|
||||
mcpu?powerpc=mpowerpc-gfxopt
|
||||
|
||||
# GCC 128-bit long double support routines.
|
||||
LIB2FUNCS_EXTRA = $(srcdir)/config/rs6000/darwin-ldouble.c
|
||||
|
||||
# Aix 3.2.x needs milli.exp for -mcpu=common
|
||||
EXTRA_PARTS = milli.exp
|
||||
milli.exp: $(srcdir)/config/rs6000/milli.exp
|
||||
|
@ -33,6 +33,7 @@ MULTILIB_MATCHES = ${MULTILIB_MATCHES_ENDIAN} \
|
||||
|
||||
# Cpu-variants supporting new exception processing only
|
||||
MULTILIB_NEW_EXCEPTIONS_ONLY = \
|
||||
*mcpu=505*/*D_OLD_EXCEPTIONS* \
|
||||
*mcpu=604*/*D_OLD_EXCEPTIONS* \
|
||||
*mcpu=750*/*D_OLD_EXCEPTIONS* \
|
||||
*mcpu=821*/*D_OLD_EXCEPTIONS* \
|
||||
|
@ -1039,11 +1039,13 @@
|
||||
})
|
||||
|
||||
(define_expand "reload_outti"
|
||||
[(parallel [(match_operand:TI 0 "memory_operand" "")
|
||||
[(parallel [(match_operand:TI 0 "" "")
|
||||
(match_operand:TI 1 "register_operand" "d")
|
||||
(match_operand:DI 2 "register_operand" "=&a")])]
|
||||
"TARGET_64BIT"
|
||||
{
|
||||
if (GET_CODE (operands[0]) != MEM)
|
||||
abort ();
|
||||
s390_load_address (operands[2], XEXP (operands[0], 0));
|
||||
operands[0] = replace_equiv_address (operands[0], operands[2]);
|
||||
emit_move_insn (operands[0], operands[1]);
|
||||
@ -1167,11 +1169,13 @@
|
||||
})
|
||||
|
||||
(define_expand "reload_outdi"
|
||||
[(parallel [(match_operand:DI 0 "memory_operand" "")
|
||||
[(parallel [(match_operand:DI 0 "" "")
|
||||
(match_operand:DI 1 "register_operand" "d")
|
||||
(match_operand:SI 2 "register_operand" "=&a")])]
|
||||
"!TARGET_64BIT"
|
||||
{
|
||||
if (GET_CODE (operands[0]) != MEM)
|
||||
abort ();
|
||||
s390_load_address (operands[2], XEXP (operands[0], 0));
|
||||
operands[0] = replace_equiv_address (operands[0], operands[2]);
|
||||
emit_move_insn (operands[0], operands[1]);
|
||||
@ -1647,11 +1651,13 @@
|
||||
})
|
||||
|
||||
(define_expand "reload_outdf"
|
||||
[(parallel [(match_operand:DF 0 "memory_operand" "")
|
||||
[(parallel [(match_operand:DF 0 "" "")
|
||||
(match_operand:DF 1 "register_operand" "d")
|
||||
(match_operand:SI 2 "register_operand" "=&a")])]
|
||||
"!TARGET_64BIT"
|
||||
{
|
||||
if (GET_CODE (operands[0]) != MEM)
|
||||
abort ();
|
||||
s390_load_address (operands[2], XEXP (operands[0], 0));
|
||||
operands[0] = replace_equiv_address (operands[0], operands[2]);
|
||||
emit_move_insn (operands[0], operands[1]);
|
||||
@ -4117,7 +4123,7 @@
|
||||
(match_operand:DF 2 "general_operand" "f,R"))
|
||||
(match_operand:DF 3 "const0_operand" "")))
|
||||
(set (match_operand:DF 0 "register_operand" "=f,f")
|
||||
(plus:DF (match_dup 1) (match_dup 2)))]
|
||||
(minus:DF (match_dup 1) (match_dup 2)))]
|
||||
"s390_match_ccmode (insn, CCSmode) && TARGET_HARD_FLOAT && TARGET_IEEE_FLOAT"
|
||||
"@
|
||||
sdbr\t%0,%2
|
||||
|
@ -92,6 +92,9 @@ Software Foundation, 59 Temple Place - Suite 330, Boston, MA
|
||||
#undef CPLUSPLUS_CPP_SPEC
|
||||
#define CPLUSPLUS_CPP_SPEC "-D_GNU_SOURCE %(cpp)"
|
||||
|
||||
#undef ASM_SPEC
|
||||
#define ASM_SPEC "%{m31&m64}%{mesa&mzarch}%{march=*}"
|
||||
|
||||
#undef LIB_SPEC
|
||||
#define LIB_SPEC "%{pthread:-lpthread} -lc"
|
||||
|
||||
|
@ -187,6 +187,8 @@ static bool sparc_function_ok_for_sibcall (tree, tree);
|
||||
static void sparc_init_libfuncs (void);
|
||||
static void sparc_output_mi_thunk (FILE *, tree, HOST_WIDE_INT,
|
||||
HOST_WIDE_INT, tree);
|
||||
static bool sparc_can_output_mi_thunk (tree, HOST_WIDE_INT,
|
||||
HOST_WIDE_INT, tree);
|
||||
static struct machine_function * sparc_init_machine_status (void);
|
||||
static bool sparc_cannot_force_const_mem (rtx);
|
||||
static rtx sparc_tls_get_addr (void);
|
||||
@ -270,7 +272,7 @@ enum processor_type sparc_cpu;
|
||||
#undef TARGET_ASM_OUTPUT_MI_THUNK
|
||||
#define TARGET_ASM_OUTPUT_MI_THUNK sparc_output_mi_thunk
|
||||
#undef TARGET_ASM_CAN_OUTPUT_MI_THUNK
|
||||
#define TARGET_ASM_CAN_OUTPUT_MI_THUNK default_can_output_mi_thunk_no_vcall
|
||||
#define TARGET_ASM_CAN_OUTPUT_MI_THUNK sparc_can_output_mi_thunk
|
||||
|
||||
#undef TARGET_RTX_COSTS
|
||||
#define TARGET_RTX_COSTS sparc_rtx_costs
|
||||
@ -1315,23 +1317,7 @@ input_operand (rtx op, enum machine_mode mode)
|
||||
|
||||
/* Check for valid MEM forms. */
|
||||
if (GET_CODE (op) == MEM)
|
||||
{
|
||||
rtx inside = XEXP (op, 0);
|
||||
|
||||
if (GET_CODE (inside) == LO_SUM)
|
||||
{
|
||||
/* We can't allow these because all of the splits
|
||||
(eventually as they trickle down into DFmode
|
||||
splits) require offsettable memory references. */
|
||||
if (! TARGET_V9
|
||||
&& GET_MODE (op) == TFmode)
|
||||
return 0;
|
||||
|
||||
return (register_operand (XEXP (inside, 0), Pmode)
|
||||
&& CONSTANT_P (XEXP (inside, 1)));
|
||||
}
|
||||
return memory_address_p (mode, inside);
|
||||
}
|
||||
return memory_address_p (mode, XEXP (op, 0));
|
||||
|
||||
return 0;
|
||||
}
|
||||
@ -3334,7 +3320,7 @@ legitimate_pic_operand_p (rtx x)
|
||||
int
|
||||
legitimate_address_p (enum machine_mode mode, rtx addr, int strict)
|
||||
{
|
||||
rtx rs1 = NULL, rs2 = NULL, imm1 = NULL, imm2;
|
||||
rtx rs1 = NULL, rs2 = NULL, imm1 = NULL;
|
||||
|
||||
if (REG_P (addr) || GET_CODE (addr) == SUBREG)
|
||||
rs1 = addr;
|
||||
@ -3374,15 +3360,14 @@ legitimate_address_p (enum machine_mode mode, rtx addr, int strict)
|
||||
else if ((REG_P (rs1) || GET_CODE (rs1) == SUBREG)
|
||||
&& (REG_P (rs2) || GET_CODE (rs2) == SUBREG))
|
||||
{
|
||||
/* We prohibit REG + REG for TFmode when there are no instructions
|
||||
which accept REG+REG instructions. We do this because REG+REG
|
||||
is not an offsetable address. If we get the situation in reload
|
||||
/* We prohibit REG + REG for TFmode when there are no quad move insns
|
||||
and we consequently need to split. We do this because REG+REG
|
||||
is not an offsettable address. If we get the situation in reload
|
||||
where source and destination of a movtf pattern are both MEMs with
|
||||
REG+REG address, then only one of them gets converted to an
|
||||
offsetable address. */
|
||||
offsettable address. */
|
||||
if (mode == TFmode
|
||||
&& !(TARGET_FPU && TARGET_ARCH64 && TARGET_V9
|
||||
&& TARGET_HARD_QUAD))
|
||||
&& ! (TARGET_FPU && TARGET_ARCH64 && TARGET_HARD_QUAD))
|
||||
return 0;
|
||||
|
||||
/* We prohibit REG + REG on ARCH32 if not optimizing for
|
||||
@ -3399,7 +3384,6 @@ legitimate_address_p (enum machine_mode mode, rtx addr, int strict)
|
||||
&& ! TARGET_CM_MEDMID
|
||||
&& RTX_OK_FOR_OLO10_P (rs2))
|
||||
{
|
||||
imm2 = rs2;
|
||||
rs2 = NULL;
|
||||
imm1 = XEXP (rs1, 1);
|
||||
rs1 = XEXP (rs1, 0);
|
||||
@ -3415,9 +3399,9 @@ legitimate_address_p (enum machine_mode mode, rtx addr, int strict)
|
||||
if (! CONSTANT_P (imm1) || tls_symbolic_operand (rs1))
|
||||
return 0;
|
||||
|
||||
/* We can't allow TFmode, because an offset greater than or equal to the
|
||||
alignment (8) may cause the LO_SUM to overflow if !v9. */
|
||||
if (mode == TFmode && !TARGET_V9)
|
||||
/* We can't allow TFmode in 32-bit mode, because an offset greater
|
||||
than the alignment (8) may cause the LO_SUM to overflow. */
|
||||
if (mode == TFmode && TARGET_ARCH32)
|
||||
return 0;
|
||||
}
|
||||
else if (GET_CODE (addr) == CONST_INT && SMALL_INT (addr))
|
||||
@ -5101,7 +5085,7 @@ static void function_arg_record_value_2
|
||||
static void function_arg_record_value_1
|
||||
(tree, HOST_WIDE_INT, struct function_arg_record_value_parms *, bool);
|
||||
static rtx function_arg_record_value (tree, enum machine_mode, int, int, int);
|
||||
static rtx function_arg_union_value (int, enum machine_mode, int);
|
||||
static rtx function_arg_union_value (int, enum machine_mode, int, int);
|
||||
|
||||
/* A subroutine of function_arg_record_value. Traverse the structure
|
||||
recursively and determine how many registers will be required. */
|
||||
@ -5445,11 +5429,19 @@ function_arg_record_value (tree type, enum machine_mode mode,
|
||||
REGNO is the hard register the union will be passed in. */
|
||||
|
||||
static rtx
|
||||
function_arg_union_value (int size, enum machine_mode mode, int regno)
|
||||
function_arg_union_value (int size, enum machine_mode mode, int slotno,
|
||||
int regno)
|
||||
{
|
||||
int nwords = ROUND_ADVANCE (size), i;
|
||||
rtx regs;
|
||||
|
||||
/* See comment in previous function for empty structures. */
|
||||
if (nwords == 0)
|
||||
return gen_rtx_REG (mode, regno);
|
||||
|
||||
if (slotno == SPARC_INT_ARG_MAX - 1)
|
||||
nwords = 1;
|
||||
|
||||
/* Unions are passed left-justified. */
|
||||
regs = gen_rtx_PARALLEL (mode, rtvec_alloc (nwords));
|
||||
|
||||
@ -5516,7 +5508,7 @@ function_arg (const struct sparc_args *cum, enum machine_mode mode,
|
||||
if (size > 16)
|
||||
abort (); /* shouldn't get here */
|
||||
|
||||
return function_arg_union_value (size, mode, regno);
|
||||
return function_arg_union_value (size, mode, slotno, regno);
|
||||
}
|
||||
/* v9 fp args in reg slots beyond the int reg slots get passed in regs
|
||||
but also have the slot allocated for them.
|
||||
@ -5796,7 +5788,7 @@ function_value (tree type, enum machine_mode mode, int incoming_p)
|
||||
if (size > 32)
|
||||
abort (); /* shouldn't get here */
|
||||
|
||||
return function_arg_union_value (size, mode, regbase);
|
||||
return function_arg_union_value (size, mode, 0, regbase);
|
||||
}
|
||||
else if (AGGREGATE_TYPE_P (type))
|
||||
{
|
||||
@ -5819,7 +5811,7 @@ function_value (tree type, enum machine_mode mode, int incoming_p)
|
||||
try to be unduly clever, and simply follow the ABI
|
||||
for unions in that case. */
|
||||
if (mode == BLKmode)
|
||||
return function_arg_union_value (bytes, mode, regbase);
|
||||
return function_arg_union_value (bytes, mode, 0, regbase);
|
||||
}
|
||||
else if (GET_MODE_CLASS (mode) == MODE_INT
|
||||
&& GET_MODE_SIZE (mode) < UNITS_PER_WORD)
|
||||
@ -9288,16 +9280,18 @@ sparc_rtx_costs (rtx x, int code, int outer_code, int *total)
|
||||
}
|
||||
}
|
||||
|
||||
/* Output code to add DELTA to the first argument, and then jump to FUNCTION.
|
||||
Used for C++ multiple inheritance. */
|
||||
/* Output the assembler code for a thunk function. THUNK_DECL is the
|
||||
declaration for the thunk function itself, FUNCTION is the decl for
|
||||
the target function. DELTA is an immediate constant offset to be
|
||||
added to THIS. If VCALL_OFFSET is nonzero, the word at address
|
||||
(*THIS + VCALL_OFFSET) should be additionally added to THIS. */
|
||||
|
||||
static void
|
||||
sparc_output_mi_thunk (FILE *file, tree thunk_fndecl ATTRIBUTE_UNUSED,
|
||||
HOST_WIDE_INT delta,
|
||||
HOST_WIDE_INT vcall_offset ATTRIBUTE_UNUSED,
|
||||
HOST_WIDE_INT delta, HOST_WIDE_INT vcall_offset,
|
||||
tree function)
|
||||
{
|
||||
rtx this, insn, funexp, delta_rtx, tmp;
|
||||
rtx this, insn, funexp;
|
||||
|
||||
reload_completed = 1;
|
||||
epilogue_completed = 1;
|
||||
@ -9315,26 +9309,73 @@ sparc_output_mi_thunk (FILE *file, tree thunk_fndecl ATTRIBUTE_UNUSED,
|
||||
|
||||
/* Add DELTA. When possible use a plain add, otherwise load it into
|
||||
a register first. */
|
||||
delta_rtx = GEN_INT (delta);
|
||||
if (!SPARC_SIMM13_P (delta))
|
||||
if (delta)
|
||||
{
|
||||
rtx scratch = gen_rtx_REG (Pmode, 1);
|
||||
rtx delta_rtx = GEN_INT (delta);
|
||||
|
||||
if (input_operand (delta_rtx, GET_MODE (scratch)))
|
||||
emit_insn (gen_rtx_SET (VOIDmode, scratch, delta_rtx));
|
||||
else
|
||||
if (! SPARC_SIMM13_P (delta))
|
||||
{
|
||||
if (TARGET_ARCH64)
|
||||
sparc_emit_set_const64 (scratch, delta_rtx);
|
||||
else
|
||||
sparc_emit_set_const32 (scratch, delta_rtx);
|
||||
rtx scratch = gen_rtx_REG (Pmode, 1);
|
||||
emit_move_insn (scratch, delta_rtx);
|
||||
delta_rtx = scratch;
|
||||
}
|
||||
|
||||
delta_rtx = scratch;
|
||||
/* THIS += DELTA. */
|
||||
emit_insn (gen_add2_insn (this, delta_rtx));
|
||||
}
|
||||
|
||||
tmp = gen_rtx_PLUS (Pmode, this, delta_rtx);
|
||||
emit_insn (gen_rtx_SET (VOIDmode, this, tmp));
|
||||
/* Add the word at address (*THIS + VCALL_OFFSET). */
|
||||
if (vcall_offset)
|
||||
{
|
||||
rtx vcall_offset_rtx = GEN_INT (vcall_offset);
|
||||
rtx scratch = gen_rtx_REG (Pmode, 1);
|
||||
|
||||
if (vcall_offset >= 0)
|
||||
abort ();
|
||||
|
||||
/* SCRATCH = *THIS. */
|
||||
emit_move_insn (scratch, gen_rtx_MEM (Pmode, this));
|
||||
|
||||
/* Prepare for adding VCALL_OFFSET. The difficulty is that we
|
||||
may not have any available scratch register at this point. */
|
||||
if (SPARC_SIMM13_P (vcall_offset))
|
||||
;
|
||||
/* This is the case if ARCH64 (unless -ffixed-g5 is passed). */
|
||||
else if (! fixed_regs[5]
|
||||
/* The below sequence is made up of at least 2 insns,
|
||||
while the default method may need only one. */
|
||||
&& vcall_offset < -8192)
|
||||
{
|
||||
rtx scratch2 = gen_rtx_REG (Pmode, 5);
|
||||
emit_move_insn (scratch2, vcall_offset_rtx);
|
||||
vcall_offset_rtx = scratch2;
|
||||
}
|
||||
else
|
||||
{
|
||||
rtx increment = GEN_INT (-4096);
|
||||
|
||||
/* VCALL_OFFSET is a negative number whose typical range can be
|
||||
estimated as -32768..0 in 32-bit mode. In almost all cases
|
||||
it is therefore cheaper to emit multiple add insns than
|
||||
spilling and loading the constant into a register (at least
|
||||
6 insns). */
|
||||
while (! SPARC_SIMM13_P (vcall_offset))
|
||||
{
|
||||
emit_insn (gen_add2_insn (scratch, increment));
|
||||
vcall_offset += 4096;
|
||||
}
|
||||
vcall_offset_rtx = GEN_INT (vcall_offset); /* cannot be 0 */
|
||||
}
|
||||
|
||||
/* SCRATCH = *(*THIS + VCALL_OFFSET). */
|
||||
emit_move_insn (scratch, gen_rtx_MEM (Pmode,
|
||||
gen_rtx_PLUS (Pmode,
|
||||
scratch,
|
||||
vcall_offset_rtx)));
|
||||
|
||||
/* THIS += *(*THIS + VCALL_OFFSET). */
|
||||
emit_insn (gen_add2_insn (this, scratch));
|
||||
}
|
||||
|
||||
/* Generate a tail call to the target function. */
|
||||
if (! TREE_USED (function))
|
||||
@ -9364,6 +9405,19 @@ sparc_output_mi_thunk (FILE *file, tree thunk_fndecl ATTRIBUTE_UNUSED,
|
||||
no_new_pseudos = 0;
|
||||
}
|
||||
|
||||
/* Return true if sparc_output_mi_thunk would be able to output the
|
||||
assembler code for the thunk function specified by the arguments
|
||||
it is passed, and false otherwise. */
|
||||
static bool
|
||||
sparc_can_output_mi_thunk (tree thunk_fndecl ATTRIBUTE_UNUSED,
|
||||
HOST_WIDE_INT delta ATTRIBUTE_UNUSED,
|
||||
HOST_WIDE_INT vcall_offset,
|
||||
tree function ATTRIBUTE_UNUSED)
|
||||
{
|
||||
/* Bound the loop used in the default method above. */
|
||||
return (vcall_offset >= -32768 || ! fixed_regs[5]);
|
||||
}
|
||||
|
||||
/* How to allocate a 'struct machine_function'. */
|
||||
|
||||
static struct machine_function *
|
||||
|
@ -2076,7 +2076,6 @@
|
||||
if (! CONSTANT_P (operands[1]) || input_operand (operands[1], DImode))
|
||||
;
|
||||
else if (TARGET_ARCH64
|
||||
&& CONSTANT_P (operands[1])
|
||||
&& GET_CODE (operands[1]) != HIGH
|
||||
&& GET_CODE (operands[1]) != LO_SUM)
|
||||
{
|
||||
|
@ -24,6 +24,6 @@ INSTALL_LIBGCC = install-multilib
|
||||
|
||||
# Assemble startup files.
|
||||
crti.o: $(srcdir)/config/sparc/sol2-ci.asm $(GCC_PASSES)
|
||||
$(GCC_FOR_TARGET) -c -o crti.o -x assembler $(srcdir)/config/sparc/sol2-ci.asm
|
||||
$(GCC_FOR_TARGET) -c -o crti.o -x assembler-with-cpp $(srcdir)/config/sparc/sol2-ci.asm
|
||||
crtn.o: $(srcdir)/config/sparc/sol2-cn.asm $(GCC_PASSES)
|
||||
$(GCC_FOR_TARGET) -c -o crtn.o -x assembler $(srcdir)/config/sparc/sol2-cn.asm
|
||||
$(GCC_FOR_TARGET) -c -o crtn.o -x assembler-with-cpp $(srcdir)/config/sparc/sol2-cn.asm
|
||||
|
@ -1,5 +1,12 @@
|
||||
# Use the system libunwind library.
|
||||
#
|
||||
# Override the default value from t-slibgcc-elf-ver and mention -lunwind
|
||||
# so that the resulting libgcc_s.so has the necessary DT_NEEDED entry for
|
||||
# libunwind.
|
||||
SHLIB_LC = -lunwind -lc
|
||||
LIB2ADDEH = $(srcdir)/unwind-sjlj.c $(srcdir)/unwind-c.c
|
||||
LIB2ADDEH = $(srcdir)/unwind-sjlj.c $(srcdir)/unwind-c.c \
|
||||
$(srcdir)/unwind-compat.c $(srcdir)/unwind-dw2-fde-compat.c
|
||||
LIB2ADDEHSTATIC = $(srcdir)/unwind-sjlj.c $(srcdir)/unwind-c.c
|
||||
|
||||
T_CFLAGS += -DUSE_LIBUNWIND_EXCEPTIONS
|
||||
TARGET_LIBGCC2_CFLAGS += -DUSE_GAS_SYMVER
|
||||
|
30
contrib/gcc/config/t-libunwind-elf
Normal file
30
contrib/gcc/config/t-libunwind-elf
Normal file
@ -0,0 +1,30 @@
|
||||
# Build libunwind for ELF with the GNU linker.
|
||||
|
||||
# Use unwind-dw2-fde-glibc
|
||||
LIBUNWIND = $(srcdir)/unwind-dw2.c $(srcdir)/unwind-dw2-fde-glibc.c
|
||||
LIBUNWINDDEP = unwind.inc unwind-dw2-fde.h unwind-dw2-fde.c
|
||||
|
||||
SHLIBUNWIND_SOVERSION = 7
|
||||
SHLIBUNWIND_SONAME = @shlib_so_name@.so.$(SHLIBUNWIND_SOVERSION)
|
||||
SHLIBUNWIND_NAME = @shlib_dir@@shlib_so_name@.so.$(SHLIBUNWIND_SOVERSION)
|
||||
|
||||
SHLIBUNWIND_LINK = $(GCC_FOR_TARGET) $(LIBGCC2_CFLAGS) -shared \
|
||||
-nodefaultlibs -Wl,-h,$(SHLIBUNWIND_SONAME) \
|
||||
-Wl,-z,text -Wl,-z,defs -o $(SHLIBUNWIND_NAME).tmp \
|
||||
@multilib_flags@ $(SHLIB_OBJS) -lc && \
|
||||
rm -f $(SHLIB_SOLINK) && \
|
||||
if [ -f $(SHLIBUNWIND_NAME) ]; then \
|
||||
mv -f $(SHLIBUNWIND_NAME) $(SHLIBUNWIND_NAME).backup; \
|
||||
else true; fi && \
|
||||
mv $(SHLIBUNWIND_NAME).tmp $(SHLIBUNWIND_NAME) && \
|
||||
$(LN_S) $(SHLIBUNWIND_NAME) $(SHLIB_SOLINK)
|
||||
|
||||
# $(slibdir) double quoted to protect it from expansion while building
|
||||
# libgcc.mk. We want this delayed until actual install time.
|
||||
SHLIBUNWIND_INSTALL = \
|
||||
$$(SHELL) $$(srcdir)/mkinstalldirs $$(DESTDIR)$$(slibdir)$(SHLIB_SLIBDIR_QUAL); \
|
||||
$(INSTALL_DATA) $(SHLIBUNWIND_NAME) \
|
||||
$$(DESTDIR)$$(slibdir)$(SHLIB_SLIBDIR_QUAL)/$(SHLIBUNWIND_SONAME); \
|
||||
rm -f $$(DESTDIR)$$(slibdir)$(SHLIB_SLIBDIR_QUAL)/$(SHLIB_SOLINK); \
|
||||
$(LN_S) $(SHLIBUNWIND_SONAME) \
|
||||
$$(DESTDIR)$$(slibdir)$(SHLIB_SLIBDIR_QUAL)/$(SHLIB_SOLINK)
|
@ -12,10 +12,14 @@ SHLIB_SLIBDIR_QUAL = @shlib_slibdir_qual@
|
||||
|
||||
SHLIB_LINK = $(GCC_FOR_TARGET) $(LIBGCC2_CFLAGS) -dynamiclib -nodefaultlibs \
|
||||
-Wl,-install_name,$(slibdir)$(SHLIB_SLIBDIR_QUAL)/$(SHLIB_SONAME) \
|
||||
-Wl,-flat_namespace -o $(SHLIB_NAME) \
|
||||
-Wl,-flat_namespace -o $(SHLIB_NAME).tmp \
|
||||
$(SHLIB_VERSTRING) \
|
||||
@multilib_flags@ $(SHLIB_OBJS) -lc && \
|
||||
rm -f $(SHLIB_SOLINK) && \
|
||||
if [ -f $(SHLIB_NAME) ]; then \
|
||||
mv -f $(SHLIB_NAME) $(SHLIB_NAME).backup; \
|
||||
else true; fi && \
|
||||
mv $(SHLIB_NAME).tmp $(SHLIB_NAME) && \
|
||||
$(LN_S) $(SHLIB_NAME) $(SHLIB_SOLINK)
|
||||
# $(slibdir) double quoted to protect it from expansion while building
|
||||
# libgcc.mk. We want this delayed until actual install time.
|
||||
|
@ -14,8 +14,12 @@ SHLIB_LC = -lc
|
||||
SHLIB_LINK = $(GCC_FOR_TARGET) $(LIBGCC2_CFLAGS) -shared -nodefaultlibs \
|
||||
-Wl,--soname=$(SHLIB_SONAME) \
|
||||
-Wl,--version-script=$(SHLIB_MAP) \
|
||||
-o $(SHLIB_NAME) @multilib_flags@ $(SHLIB_OBJS) $(SHLIB_LC) && \
|
||||
-o $(SHLIB_NAME).tmp @multilib_flags@ $(SHLIB_OBJS) $(SHLIB_LC) && \
|
||||
rm -f $(SHLIB_SOLINK) && \
|
||||
if [ -f $(SHLIB_NAME) ]; then \
|
||||
mv -f $(SHLIB_NAME) $(SHLIB_NAME).backup; \
|
||||
else true; fi && \
|
||||
mv $(SHLIB_NAME).tmp $(SHLIB_NAME) && \
|
||||
$(LN_S) $(SHLIB_NAME) $(SHLIB_SOLINK)
|
||||
# $(slibdir) double quoted to protect it from expansion while building
|
||||
# libgcc.mk. We want this delayed until actual install time.
|
||||
|
@ -10,9 +10,13 @@ SHLIB_SLIBDIR_QUAL = @shlib_slibdir_qual@
|
||||
|
||||
SHLIB_LINK = $(GCC_FOR_TARGET) $(LIBGCC2_CFLAGS) -shared -nodefaultlibs \
|
||||
-Wl,-h,$(SHLIB_SONAME) -Wl,-z,text -Wl,-z,defs \
|
||||
-Wl,-M,$(SHLIB_MAP) -o $(SHLIB_NAME) \
|
||||
-Wl,-M,$(SHLIB_MAP) -o $(SHLIB_NAME).tmp \
|
||||
@multilib_flags@ $(SHLIB_OBJS) -lc && \
|
||||
rm -f $(SHLIB_SOLINK) && \
|
||||
if [ -f $(SHLIB_NAME) ]; then \
|
||||
mv -f $(SHLIB_NAME) $(SHLIB_NAME).backup; \
|
||||
else true; fi && \
|
||||
mv $(SHLIB_NAME).tmp $(SHLIB_NAME) && \
|
||||
$(LN_S) $(SHLIB_NAME) $(SHLIB_SOLINK)
|
||||
# $(slibdir) double quoted to protect it from expansion while building
|
||||
# libgcc.mk. We want this delayed until actual install time.
|
||||
|
1766
contrib/gcc/configure
vendored
1766
contrib/gcc/configure
vendored
File diff suppressed because it is too large
Load Diff
@ -979,20 +979,10 @@ AC_ARG_ENABLE(sjlj-exceptions,
|
||||
AC_DEFINE_UNQUOTED(CONFIG_SJLJ_EXCEPTIONS, $sjlj,
|
||||
[Define 0/1 to force the choice for exception handling model.])])
|
||||
|
||||
if test x$host = x$target; then
|
||||
AC_CHECK_LIB(unwind, main, use_libunwind_default=yes, use_libunwind_default=no)
|
||||
else
|
||||
use_libunwind_default=no
|
||||
fi
|
||||
# Use libunwind based exception handling.
|
||||
AC_ARG_ENABLE(libunwind-exceptions,
|
||||
[ --enable-libunwind-exceptions force use libunwind for exceptions],
|
||||
use_libunwind_exceptions=$enableval,
|
||||
use_libunwind_exceptions=$use_libunwind_default)
|
||||
if test x"$use_libunwind_exceptions" = xyes; then
|
||||
AC_DEFINE(USE_LIBUNWIND_EXCEPTIONS, 1,
|
||||
[Define if gcc should use -lunwind.])
|
||||
fi
|
||||
# For platforms with the unwind ABI which includes an unwind library,
|
||||
# libunwind, we can choose to use the system libunwind.
|
||||
AC_ARG_WITH(system-libunwind,
|
||||
[ --with-system-libunwind use installed libunwind])
|
||||
|
||||
# --------------------------------------------------------
|
||||
# Build, host, and target specific configuration fragments
|
||||
@ -1865,6 +1855,12 @@ gcc_GAS_CHECK_FEATURE([.weak], gcc_cv_as_weak,
|
||||
[ .weak foobar],,
|
||||
[AC_DEFINE(HAVE_GAS_WEAK, 1, [Define if your assembler supports .weak.])])
|
||||
|
||||
gcc_GAS_CHECK_FEATURE([.nsubspa comdat], gcc_cv_as_nsubspa_comdat,
|
||||
[2,15,91],,
|
||||
[ .SPACE $TEXT$
|
||||
.NSUBSPA $CODE$,COMDAT],,
|
||||
[AC_DEFINE(HAVE_GAS_NSUBSPA_COMDAT, 1, [Define if your assembler supports .nsubspa comdat option.])])
|
||||
|
||||
# .hidden needs to be supported in both the assembler and the linker,
|
||||
# because GNU LD versions before 2.12.1 have buggy support for STV_HIDDEN.
|
||||
# This is irritatingly difficult to feature test for; we have to check the
|
||||
@ -2407,7 +2403,7 @@ foo:
|
||||
[if test x$gcc_cv_objdump != x \
|
||||
&& $gcc_cv_objdump -s -j .text conftest.o 2> /dev/null \
|
||||
| grep ' 82106000 82106000' > /dev/null 2>&1; then
|
||||
gcc_cv_as_offsetable_lo10=yes
|
||||
gcc_cv_as_sparc_offsetable_lo10=yes
|
||||
fi],
|
||||
[AC_DEFINE(HAVE_AS_OFFSETABLE_LO10, 1,
|
||||
[Define if your assembler supports offsetable %lo().])])
|
||||
@ -2627,6 +2623,25 @@ if test x"$gcc_cv_ld_pie" = xyes; then
|
||||
fi
|
||||
AC_MSG_RESULT($gcc_cv_ld_pie)
|
||||
|
||||
AC_MSG_CHECKING(linker -Bstatic/-Bdynamic option)
|
||||
gcc_cv_ld_static_dynamic=no
|
||||
if test $in_tree_ld = yes ; then
|
||||
if test "$gcc_cv_gld_major_version" -eq 2 -a "$gcc_cv_gld_minor_version" -ge 10; then
|
||||
gcc_cv_ld_static_dynamic=yes
|
||||
fi
|
||||
elif test x$gcc_cv_ld != x; then
|
||||
# Check if linker supports -Bstatic/-Bdynamic option
|
||||
if $gcc_cv_ld --help 2>/dev/null | grep -- -Bstatic > /dev/null \
|
||||
&& $gcc_cv_ld --help 2>/dev/null | grep -- -Bdynamic > /dev/null; then
|
||||
gcc_cv_ld_static_dynamic=yes
|
||||
fi
|
||||
fi
|
||||
if test x"$gcc_cv_ld_static_dynamic" = xyes; then
|
||||
AC_DEFINE(HAVE_LD_STATIC_DYNAMIC, 1,
|
||||
[Define if your linker supports -Bstatic/-Bdynamic option.])
|
||||
fi
|
||||
AC_MSG_RESULT($gcc_cv_ld_static_dynamic)
|
||||
|
||||
case "$target" in
|
||||
*-*-linux*)
|
||||
AC_CACHE_CHECK(linker --as-needed support,
|
||||
@ -3100,6 +3115,9 @@ AC_SUBST(target_cpu_default)
|
||||
|
||||
AC_SUBST_FILE(language_hooks)
|
||||
|
||||
sinclude(../config/gcc-lib-path.m4)
|
||||
TL_AC_GNU_MAKE_GCC_LIB_PATH
|
||||
|
||||
# If it doesn't already exist, create document directory
|
||||
echo "checking for the document directory." 1>&2
|
||||
if test -d doc ; then
|
||||
|
@ -4048,21 +4048,6 @@ __cxa_demangle (mangled_name, output_buffer, length, status)
|
||||
return NULL;
|
||||
}
|
||||
|
||||
/* The specification for __cxa_demangle() is that if the mangled
|
||||
name could be either an extern "C" identifier, or an internal
|
||||
built-in type name, then we resolve it as the identifier. All
|
||||
internal built-in type names are a single lower case character.
|
||||
Frankly, this simplistic disambiguation doesn't make sense to me,
|
||||
but it is documented, so we implement it here. */
|
||||
if (IS_LOWER (mangled_name[0])
|
||||
&& mangled_name[1] == '\0'
|
||||
&& cplus_demangle_builtin_types[mangled_name[0] - 'a'].name != NULL)
|
||||
{
|
||||
if (status != NULL)
|
||||
*status = -2;
|
||||
return NULL;
|
||||
}
|
||||
|
||||
demangled = d_demangle (mangled_name, DMGL_PARAMS | DMGL_TYPES, &alc);
|
||||
|
||||
if (demangled == NULL)
|
||||
|
@ -1,3 +1,623 @@
|
||||
2005-05-19 Release Manager
|
||||
|
||||
* GCC 3.4.4 released.
|
||||
|
||||
2005-05-08 Nathan Sidwell <nathan@codesourcery.com>
|
||||
|
||||
PR c++/21427
|
||||
Backport 2005-03-01 Nathan Sidwell <nathan@codesourcery.com>
|
||||
* class.c (update_vtable_entry_for_fn): Don't crash on invalid
|
||||
covariancy.
|
||||
|
||||
* cp-tree.h (THUNK_TARGET): Expand comment.
|
||||
* method.c (use_thunk): Make sure we also use the target, if that
|
||||
is a thunk.
|
||||
|
||||
Backport 2005-02-11 Nathan Sidwell <nathan@codesourcery.com>
|
||||
* class.c (update_vtable_entry_for_fn): Walk the covariant's binfo
|
||||
chain rather than using lookup_base.
|
||||
|
||||
2005-05-04 Mark Mitchell <mark@codesourcery.com>
|
||||
|
||||
Backport:
|
||||
2004-12-21 Mark Mitchell <mark@codesourcery.com>
|
||||
PR c++/19034
|
||||
* tree.c (cp_tree_equal): Handle OVERLOAD.
|
||||
|
||||
2005-05-02 Mark Mitchell <mark@codesourcery.com>
|
||||
|
||||
Revert:
|
||||
2005-05-01 Mark Mitchell <mark@codesourcery.com>
|
||||
* typeck.c (unary_complex_lvalue): In a template, always refuse
|
||||
simplifications.
|
||||
|
||||
2005-05-01 Mark Mitchell <mark@codesourcery.com>
|
||||
|
||||
Backport:
|
||||
2005-02-22 Mark Mitchell <mark@codesourcery.com>
|
||||
PR c++/19991
|
||||
* init.c (decl_constant_value): Iterate if the value of a decl
|
||||
is itself a constant.
|
||||
|
||||
2005-05-01 Mark Mitchell <mark@codesourcery.com>
|
||||
|
||||
Backport:
|
||||
2004-12-22 Mark Mitchell <mark@codesourcery.com>
|
||||
PR c++/18464
|
||||
* call.c (build_this): In templates, do not bother with
|
||||
build_unary_op.
|
||||
* typeck.c (unary_complex_lvalue): In a template, always refuse
|
||||
simplifications.
|
||||
|
||||
2005-04-25 Roger Sayle <roger@eyesopen.com>
|
||||
Mark Mitchell <mark@codesourcery.com>
|
||||
|
||||
PR c++/20995
|
||||
Partial backport from mainline.
|
||||
2004-09-27 Mark Mitchell <mark@codesourcery.com>
|
||||
* tree.c (fold_if_not_in_template): New function.
|
||||
* cp-tree.h (fold_if_not_in_template): Prototype here.
|
||||
* call.c (build_conditional_expr): Use fold_if_not_in_template.
|
||||
* typeck.c (build_binary_op): Likewise.
|
||||
|
||||
2005-04-16 Mark Mitchell <mark@codesourcery.com>
|
||||
|
||||
PR c++/21025
|
||||
* typeck.c (cxx_sizeof_or_alignof_type): Check whether the type to
|
||||
which sizeof/alignof is dependent, rather than just whether we are
|
||||
processing_template_decl.
|
||||
|
||||
2005-04-06 Jason Merrill <jason@redhat.com>
|
||||
|
||||
PR c++/19312
|
||||
* tree.c (stabilize_init): Don't bother trying to stabilize
|
||||
something with no side-effects.
|
||||
|
||||
2005-04-04 Mark Mitchell <mark@codesourcery.com>
|
||||
|
||||
PR c++/20679
|
||||
* parser.c (cp_parser_template_name): Fix thinko.
|
||||
|
||||
2005-04-03 Gabriel Dos Reis <gdr@integrable-solutions.net>
|
||||
|
||||
PR c++/18644
|
||||
* call.c (build_new_op): Remove check for -Wsynth.
|
||||
|
||||
2005-03-21 Paolo Carlini <pcarlini@suse.de>
|
||||
|
||||
PR c++/20147
|
||||
* semantics.c (finish_stmt_expr_expr): Return immediately
|
||||
if error_operand_p (expr).
|
||||
|
||||
2005-03-19 Kriang Lerdsuwanakij <lerdsuwa@users.sourceforge.net>
|
||||
|
||||
PR c++/20240
|
||||
* decl.c (decls_match): Compare context of VAR_DECL.
|
||||
|
||||
2005-03-19 Kriang Lerdsuwanakij <lerdsuwa@users.sourceforge.net>
|
||||
|
||||
PR c++/20333
|
||||
* parser.c (cp_parser_postfix_expression) <case RID_TYPENAME>:
|
||||
Check the return value of cp_parser_nested_name_specifier.
|
||||
|
||||
2005-03-08 Mark Mitchell <mark@codesourcery.com>
|
||||
|
||||
PR c++/20142
|
||||
* init.c (build_vec_init): When determining whether or not the
|
||||
element type has an asignment operator, look through all array
|
||||
dimensions.
|
||||
|
||||
2005-03-06 Kriang Lerdsuwanakij <lerdsuwa@users.sourceforge.net>
|
||||
|
||||
PR c++/19311
|
||||
* init.c (build_offset_ref): Don't build non-dependent SCOPE_REF.
|
||||
* pt.c (build_non_dependent_expr): Don't build NON_DEPENDENT_EXPR
|
||||
for OFFSET_TYPE.
|
||||
* typeck.c (build_x_unary_op): Don't build non-dependent SCOPE_REF.
|
||||
Also set PTRMEM_OK_P for NON_DEPENDENT_EXPR.
|
||||
(build_unary_op): Handle building ADDR_EXPR of OFFSET_REF inside
|
||||
template.
|
||||
|
||||
2005-03-02 Alexandre Oliva <aoliva@redhat.com>
|
||||
|
||||
* name-lookup.c (push_overloaded_decl): Don't error if the new
|
||||
decl matches the old one.
|
||||
* decl.c (redeclaration_error_message): Likewise.
|
||||
|
||||
2005-02-24 Jakub Jelinek <jakub@redhat.com>
|
||||
|
||||
PR c++/20175
|
||||
* decl.c (reshape_init): Don't warn about missing braces if STRING_CST
|
||||
initializes a char/wchar_t array.
|
||||
|
||||
2005-02-21 Alexandre Oliva <aoliva@redhat.com>
|
||||
|
||||
PR c++/20028
|
||||
* class.c (finish_struct): Initialize TYPE_SIZE_UNIT of a
|
||||
template along with TYPE_SIZE.
|
||||
|
||||
2005-02-14 Mark Mitchell <mark@codesourcery.com>
|
||||
|
||||
* decl.c (reshape_init): Use explicit quotes in error message
|
||||
instead of %q.
|
||||
|
||||
2005-02-12 Kriang Lerdsuwanakij <lerdsuwa@users.sourceforge.net>
|
||||
|
||||
PR c++/14479
|
||||
PR c++/19487
|
||||
* pt.c (maybe_check_template_type): Remove.
|
||||
* cp-tree.h (maybe_check_template_type): Remove prototype.
|
||||
* name-lookup.c (maybe_process_template_type_declaration): Don't
|
||||
use maybe_check_template_type.
|
||||
|
||||
2005-02-10 Mark Mitchell <mark@codesourcery.com>
|
||||
|
||||
PR c++/19755
|
||||
* decl.c (reshape_init): Issue warnings about missing braces.
|
||||
|
||||
2005-02-09 Mark Mitchell <mark@codesourcery.com>
|
||||
|
||||
* parser.c (cp_parser_unqualified_id): Initialize type_decl.
|
||||
|
||||
PR c++/19787
|
||||
* call.c (initialize_reference): Robustify.
|
||||
|
||||
PR c++/19762
|
||||
* parser.c (cp_parser_unqualified_id): Avoid creating destructor
|
||||
names with invalid types.
|
||||
|
||||
PR c++/19739
|
||||
* parser.c (cp_parser_attributes_list): Allow empty lists.
|
||||
|
||||
2005-02-08 Mark Mitchell <mark@codesourcery.com>
|
||||
|
||||
PR c++/19733
|
||||
* cvt.c (convert_to_void): Issue errors about pseudo-destructor
|
||||
expressions.
|
||||
|
||||
2005-02-01 Alexandre Oliva <aoliva@redhat.com>
|
||||
|
||||
PR c++/18757
|
||||
PR c++/19366
|
||||
PR c++/19499
|
||||
* parser.c (cp_parser_template_id): Revert 2004-12-09's patch.
|
||||
Issue an error when creating the template id.
|
||||
* pt.c (fn_type_unification): Return early if the explicit
|
||||
template arg list is an error_mark_node.
|
||||
|
||||
2005-01-27 J"orn Rennecke <joern.rennecke@st.com>
|
||||
|
||||
PR c++/18370
|
||||
* parser.c (cp_parser_initializer_clause): Initialize *non_constant_p.
|
||||
|
||||
2005-01-19 Kriang Lerdsuwanakij <lerdsuwa@users.sourceforge.net>
|
||||
|
||||
PR c++/19375
|
||||
* semantics.c (finish_id_expression): Disable access checking for
|
||||
already lookuped FIELD_DECL.
|
||||
|
||||
2005-01-19 Kriang Lerdsuwanakij <lerdsuwa@users.sourceforge.net>
|
||||
|
||||
PR c++/19258
|
||||
* parser.c (cp_parser_late_parsing_default_args): Handle friend
|
||||
defined in class.
|
||||
* pt.c (push_access_scope, pop_access_scope): Likewise.
|
||||
|
||||
2005-01-15 Jakub Jelinek <jakub@redhat.com>
|
||||
|
||||
PR c++/19263
|
||||
* typeck2.c (split_nonconstant_init_1) <case VECTOR_TYPE>: Put a copy
|
||||
of CONSTRUCTOR's node into MODIFY_EXPR, as the original is modified.
|
||||
Store code to *pcode.
|
||||
|
||||
2004-12-28 Jakub Jelinek <jakub@redhat.com>
|
||||
|
||||
PR c++/18384, c++/18327
|
||||
* decl.c (reshape_init_array): Use UHWI type for max_index_cst
|
||||
and index. Convert max_index to size_type_node if it isn't
|
||||
host_integerp (, 1).
|
||||
|
||||
2004-12-23 Alexandre Oliva <aoliva@redhat.com>
|
||||
|
||||
PR c++/18962
|
||||
* pt.c (check_explicit_specialization): Use the argument list from
|
||||
the definition in a template function specialization definition.
|
||||
|
||||
2004-12-23 Alexandre Oliva <aoliva@redhat.com>
|
||||
|
||||
PR c++/18757
|
||||
* parser.c (cp_parser_template_id): Don't create a CPP_TEMPLATE_ID
|
||||
if parsing failed.
|
||||
|
||||
2004-12-17 Nathan Sidwell <nathan@codesourcery.com>
|
||||
|
||||
PR c++/18975
|
||||
* method.c (do_build_copy_constructor): Refactor. Don't const
|
||||
qualify a mutable field.
|
||||
(do_build_assign_ref): Likewise.
|
||||
|
||||
2004-12-10 Volker Reichelt <reichelt@igpm.rwth-aachen.de>
|
||||
|
||||
PR c++/18731
|
||||
* parser.c (cp_parser_class_head): Reject typedef-name in class head.
|
||||
|
||||
2004-12-09 Nathan Sidwell <nathan@codesourcery.com>
|
||||
|
||||
PR c++/16681
|
||||
* init.c (build_zero_init): Build a RANGE_EXPR for an array
|
||||
initializer.
|
||||
|
||||
2004-12-08 Kriang Lerdsuwanakij <lerdsuwa@users.sourceforge.net>
|
||||
|
||||
PR c++/18100
|
||||
* name-lookup.c (push_class_level_binding): Diagnose nested
|
||||
class template with the same name as enclosing class.
|
||||
|
||||
2004-12-04 Kriang Lerdsuwanakij <lerdsuwa@users.sourceforge.net>
|
||||
|
||||
PR c++/17011, c++/17971
|
||||
* pt.c (tsubst_copy) <FIELD_DECL case>: Check and diagnose
|
||||
invalid field.
|
||||
(tsubst_copy_and_build) <COMPONENT_REF case>: Check
|
||||
error_mark_node after member substitution.
|
||||
* semantics.c (finish_id_expression): Call
|
||||
finish_non_static_data_member for dependent FIELD_DECL.
|
||||
|
||||
2004-12-02 Kriang Lerdsuwanakij <lerdsuwa@users.sourceforge.net>
|
||||
|
||||
PR c++/18123
|
||||
* parser.c (cp_parser_type_specifier): Don't create new enum
|
||||
type if it is not in the form 'enum [identifier] { [...] };'.
|
||||
Catch template declaration of enum.
|
||||
|
||||
2004-12-01 Nathan Sidwell <nathan@codesourcery.com>
|
||||
|
||||
PR c++/17431
|
||||
* call.c (standard_conversion): Add FLAGS parameter. Do not allow
|
||||
derived to base conversion when checking constructor
|
||||
accessibility.
|
||||
(implicit_conversion): Pass FLAGS to standard_conversion.
|
||||
(check_constructir_callable): Disallow conversion functions.
|
||||
|
||||
2004-11-12 Mark Mitchell <mark@codesourcery.com>
|
||||
|
||||
PR c++/18389
|
||||
* decl.c (start_decl): Make sure to set *pop_scope_p. Return
|
||||
error_mark_node to indicate errors.
|
||||
|
||||
PR c++/18436
|
||||
* pt.c (tsubst_copy_and_build): Do not do Koenig lookup when an
|
||||
unqualified name resolves to a member function.
|
||||
|
||||
PR c++/18407
|
||||
* pt.c (tsubst_copy_and_build): Handle qualified names used from a
|
||||
derived class correctly.
|
||||
|
||||
2004-11-04 Release Manager
|
||||
|
||||
* GCC 3.4.3 released.
|
||||
|
||||
2004-10-31 Mark Mitchell <mark@codesourcery.com>
|
||||
|
||||
PR c++/15172
|
||||
* typeck2.c (store_init_value): Use split_nonconstant_init even
|
||||
for types that require construction.
|
||||
|
||||
2004-10-28 Mark Mitchell <mark@codesourcery.com>
|
||||
|
||||
PR c++/17132
|
||||
* pt.c (instantiate_class_template): Increment
|
||||
processing_template_decl when substituting into a member class
|
||||
template.
|
||||
|
||||
2004-10-27 Mark Mitchell <mark@codesourcery.com>
|
||||
|
||||
PR c++/18140
|
||||
* parser.c (cp_parser_next_token_ends_template_argument_p): Do not
|
||||
include ">>".
|
||||
|
||||
2004-10-27 Andrew Pinski <pinskia@physics.uc.edu>
|
||||
|
||||
PR c++/13560
|
||||
* error.c (cp_error_at): Output the context as it might be
|
||||
different file as the other location.
|
||||
|
||||
2004-10-26 Mark Mitchell <mark@codesourcery.com>
|
||||
|
||||
PR c++/18093
|
||||
* search.c (current_scope): Return the innermost non-block scope,
|
||||
not the innermost non-block, non-namespace scope.
|
||||
(at_namespace_scope_p): Adjust accordingly.
|
||||
(dfs_accessible_post): Do not pass namespaces to is_friend.
|
||||
(dfs_walk_once_accessible_r): Likewise.
|
||||
* decl.c (grokvardecl): Adjust call to current_scope.
|
||||
(build_enumerator): Likewise.
|
||||
* parser.c (cp_parser_using_declaration): Likewise.
|
||||
(cp_parser_direct_declarator): Use at_namespace_scope_p instead of
|
||||
current_scope.
|
||||
(cp_parser_class_head): Adjust call to current_scope.
|
||||
* name-lookup.c (do_namespace_alias): Set the DECL_CONTEXT for the
|
||||
alias.
|
||||
|
||||
PR c++/18020
|
||||
* pt.c (tusbst_copy_and_build): Resolve enumeration constants to
|
||||
their underlying values.
|
||||
|
||||
2004-10-17 Andrew Pinski <pinskia@physics.uc.edu>
|
||||
|
||||
PR c++/16301
|
||||
* name-lookup.c (parse_using_directive): If we have a
|
||||
error_mark_node, do not set the decl namespace associations
|
||||
on it.
|
||||
|
||||
2004-10-14 Mark Mitchell <mark@codesourcery.com>
|
||||
|
||||
PR c++/17976
|
||||
* decl.c (cp_finish_decl): Do not call expand_static_init more
|
||||
than once for a single variable.
|
||||
|
||||
2004-10-11 Mark Mitchell <mark@codesourcery.com>
|
||||
|
||||
PR c++/15786
|
||||
* parser.c (cp_parser_declarator): Add member_p parameter.
|
||||
(cp_parser_condition): Adjust calls to cp_parser_declarator.
|
||||
(cp_parser_explicit_instantiation): Likewise.
|
||||
(cp_parser_init_declarator): Likewise.
|
||||
(cp_parser_direct_declarator): Add member_p parameter. Do not
|
||||
parse tentatively when parsing the parameters to a member.
|
||||
(cp_parser_type_id): Adjust calls to cp_parser_declarator.
|
||||
(cp_parser_parameter_declaration): Likewise.
|
||||
(cp_parser_member_declaration): Likewise.
|
||||
(cp_parser_exception_declaration): Likewise.
|
||||
|
||||
2004-10-11 Mark Mitchell <mark@codesourcery.com>
|
||||
|
||||
* decl2.c (finish_anon_union): Robustify.
|
||||
|
||||
2004-10-10 Mark Mitchell <mark@codesourcery.com>
|
||||
|
||||
PR c++/17393
|
||||
* decl.c (grokdeclarator): Robustify error-recovery on invalid
|
||||
declarations.
|
||||
|
||||
2004-10-09 Mark Mitchell <mark@codesourcery.com>
|
||||
|
||||
PR c++/17821
|
||||
* parser.c (cp_parser_postfix_dot_deref_expression): If the
|
||||
pseduo-destructor-name production does not work, fall back to the
|
||||
ordinary production.
|
||||
|
||||
PR c++/17826
|
||||
* tree.c (cp_tree_equal): Handle a BASELINK.
|
||||
|
||||
2004-10-09 Mark Mitchell <mark@codesourcery.com>
|
||||
|
||||
PR c++/17524
|
||||
* cp-tree.h (check_var_type): New function.
|
||||
* decl.c (check_var_type): New function, split out from ...
|
||||
(grokdeclarator): ... here.
|
||||
* pt.c (tsubst_decl): Use check_var_type.
|
||||
|
||||
PR c++/17685
|
||||
* decl.c (grokdeclarator): Disallow declarations of operators as
|
||||
non-functions.
|
||||
|
||||
2004-10-08 Volker Reichelt <reichelt@igpm.rwth-aachen.de>
|
||||
|
||||
PR c++/17868
|
||||
* error.c (dump_expr): Add missing case for RDIV_EXPR.
|
||||
|
||||
2004-10-08 Nathan Sidwell <nathan@codesourcery.com>
|
||||
|
||||
PR c++/17829
|
||||
* parser.c (cp_parser_postfix_expression): Inhibit Koenig when
|
||||
unqualified lookup finds a member function.
|
||||
|
||||
2004-09-28 Roger Sayle <roger@eyesopen.com>
|
||||
|
||||
PR driver/17537
|
||||
* g++spec.c (lang_specific_driver): Unrecognized libraries, other
|
||||
than -lc and -lm, may require linking against libstc++.
|
||||
|
||||
2004-09-27 Mark Mitchell <mark@codesourcery.com>
|
||||
|
||||
PR c++/17585
|
||||
* cp-tree.h (shared_member_p): Declare.
|
||||
* search.c (shared_member_p): Give it external linkage.
|
||||
* semantics.c (finish_qualified_id_expr): Use it.
|
||||
(finish_id_expression): Likewise.
|
||||
|
||||
2004-09-22 Giovanni Bajo <giovannibajo@gcc.gnu.org>
|
||||
|
||||
PR c++/14179
|
||||
* parser.c (cp_parser_initializer): Speed up parsing of simple
|
||||
literals as initializers.
|
||||
|
||||
2004-09-21 Giovanni Bajo <giovannibajo@gcc.gnu.org>
|
||||
|
||||
PR c++/14179
|
||||
* decl.c (reshape_init): Extract array handling into...
|
||||
(reshape_init_array): New function. Use integers instead of trees
|
||||
for indices. Handle out-of-range designated initializers.
|
||||
|
||||
2004-09-16 Mark Mitchell <mark@codesourcery.com>
|
||||
|
||||
PR c++/17501
|
||||
* parser.c (cp_parser_nested_name_specifier): Do not resolve
|
||||
typename types if the user explicitly said "typename".
|
||||
|
||||
2004-09-13 Mark Mitchell <mark@codesourcery.com>
|
||||
|
||||
PR c++/16162
|
||||
* parser.c (cp_parser_id_expression): Correct value for
|
||||
is_declarator.
|
||||
(cp_parser_nested_name_specifier_opt): Look through typenames as
|
||||
necessary.
|
||||
(cp_parser_template_name): Honor check_dependency_p.
|
||||
|
||||
2004-09-13 Mark Mitchell <mark@codesourcery.com>
|
||||
|
||||
PR c++/17327
|
||||
* pt.c (unify): Add ENUMERAL_TYPE case. Replace sorry with
|
||||
gcc_unreacable.
|
||||
|
||||
2004-09-06 Release Manager
|
||||
|
||||
* GCC 3.4.2 released.
|
||||
|
||||
2004-08-25 Roger Sayle <roger@eyesopen.com>
|
||||
|
||||
PR middle-end/16693
|
||||
PR tree-optimization/16372
|
||||
* decl.c (finish_enum): Make the precision of the enumerated type
|
||||
the same width as the underlying integer type.
|
||||
|
||||
2004-08-24 Jason Merrill <jason@redhat.com>
|
||||
|
||||
PR c++/16851
|
||||
* tree.c (stabilize_init): See through a COMPOUND_EXPR.
|
||||
|
||||
PR c++/15461
|
||||
* semantics.c (nullify_returns_r): Replace a DECL_STMT
|
||||
for the NRV with an INIT_EXPR.
|
||||
|
||||
2004-08-24 Nathan Sidwell <nathan@codesourcery.com>
|
||||
|
||||
PR c++/16889
|
||||
* (is_subobject_of_p): Resurrect & optimize.
|
||||
(lookup_field_r): Use it.
|
||||
|
||||
2004-08-24 Kriang Lerdsuwanakij <lerdsuwa@users.sourceforge.net>
|
||||
|
||||
PR c++/16706
|
||||
* search.c (friend_accessible_p): Increment processing_template_decl
|
||||
when deal with TEMPLATE_DECL of SCOPE.
|
||||
|
||||
2004-08-23 Janis Johnson <janis187@us.ibm.com>
|
||||
|
||||
Backports from mainline:
|
||||
|
||||
2004-02-27 Ziemowit Laski <zlaski@apple.com>
|
||||
2004-03-24 Ziemowit Laski <zlaski@apple.com>
|
||||
|
||||
* Make-lang.in (cp/mangle.o): Depend on $(TARGET_H).
|
||||
* mangle.c (write_type): Add call to 'mangle_fundamental_type'
|
||||
target hook.
|
||||
* tree.c (pod_type_p): Treat VECTOR_TYPEs as PODs.
|
||||
|
||||
2004-08-19 Mark Mitchell <mark@codesourcery.com>
|
||||
|
||||
PR c++/15890
|
||||
* pt.c (push_template_decl_real): Disallow template allocation
|
||||
functions with fewer than two parameters.
|
||||
|
||||
2004-08-18 Mark Mitchell <mark@codesourcery.com>
|
||||
|
||||
PR c++/17068
|
||||
* pt.c (dependent_template_p): Treat IDENTIFIER_NODEs as
|
||||
dependent.
|
||||
|
||||
2004-08-17 Mark Mitchell <mark@codesourcery.com>
|
||||
|
||||
PR c++/16246
|
||||
* pt.c (unify): Make sure that non-type arguments have the same
|
||||
type as the corresponding parameter.
|
||||
|
||||
2004-08-12 Mark Mitchell <mark@codesourcery.com>
|
||||
|
||||
PR c++/16273
|
||||
* class.c (count_depth_data): New type.
|
||||
(dfs_depth_post): New function.
|
||||
(dfs_depth_q): Likewise.
|
||||
(find_final_overrider_data_s): Change type of vpath.
|
||||
Add vpath_list.
|
||||
(dfs_find_final_overrider_1): New function.
|
||||
(dfs_find_final_overrider): Use it.
|
||||
(dfs_find_final_overrider_q): Adjust use of vpath.
|
||||
(dfs_find_final_overrider_post): Likewise.
|
||||
(find_final_overrider): Use dfs_depth. Allocate and deallocate
|
||||
vpath_list.
|
||||
|
||||
2004-08-12 Jan Beulich <jbeulich@novell.com>
|
||||
|
||||
* parser.c (cp_parser_asm_definition): Properly consume scope operator
|
||||
tokens preceding the clobbers. Don't check for scope operator
|
||||
following inputs. Simplify inputs handling to match that now used for
|
||||
clobbers.
|
||||
|
||||
2004-08-11 Mark Mitchell <mark@codesourcery.com>
|
||||
|
||||
PR c++/16698
|
||||
* except.c (build_throw): Allocate cleanup_type and the function
|
||||
for __cxa_throw separately.
|
||||
|
||||
2004-08-11 Mark Mitchell <mark@codesourcery.com>
|
||||
|
||||
PR c++/16717
|
||||
* semantics.c (expand_body): Do not update static_ctors and
|
||||
static_dtors here.
|
||||
(expand_or_defer_fn): Do it here, instead.
|
||||
|
||||
PR c++/16853
|
||||
* call.c (standard_conversion): Do not accept conversions between
|
||||
pointers to members if the class types are unrelated.
|
||||
|
||||
PR c++/16870
|
||||
* pt.c (tsubst): Just return the unknown_type_node.
|
||||
|
||||
PR c++/16964
|
||||
* parser.c (cp_parser_class_specifier): Robustify.
|
||||
|
||||
PR c++/16904
|
||||
* pt.c (tsubst_copy_and_build): Complain about invalid
|
||||
qualification.
|
||||
|
||||
PR c++/16929
|
||||
* pt.c (tsubst_default_argument): Clear out current_class_ptr and
|
||||
current_class_ref while tsubsting.
|
||||
|
||||
2004-08-01 Mark Mitchell <mark@codesourcery.com>
|
||||
|
||||
PR c++/16224
|
||||
* name-lookup.c (decl_namespace): Remove.
|
||||
(current_decl_namespace): Use decl_namespace_context instead of
|
||||
decl_namespace.
|
||||
(push_decl_namespace): Likewise.
|
||||
(arg_assoc_class): Likewise.
|
||||
(arg_assoc_type): Likewise.
|
||||
* pt.c (check_specialization_namespace): New function.
|
||||
(maybe_process_partial_specialization): Use it.
|
||||
(register_specialization): Likewise.
|
||||
|
||||
2004-08-01 Mark Mitchell <mark@codesourcery.com>
|
||||
|
||||
PR c++/16489
|
||||
* cp-tree.h (DECL_INTEGRAL_CONSTANT_VAR_P): New macro.
|
||||
* call.c (null_ptr_cst_p): Handle variables with constant
|
||||
initializers.
|
||||
* pt.c (convert_nontype_argument): Use
|
||||
DECL_INTEGRAL_CONSTANT_VAR_P.
|
||||
* semantics.c (finish_id_expression): Likewise.
|
||||
|
||||
PR c++/16529
|
||||
* decl.c (duplicate_decls): Reject duplicate namespace
|
||||
declarations.
|
||||
|
||||
PR c++/16810
|
||||
* typeck.c (build_ptrmemfunc): Loosen assertion.
|
||||
|
||||
2004-07-28 Kriang Lerdsuwanakij <lerdsuwa@users.sourceforge.net>
|
||||
|
||||
PR c++/13092
|
||||
* init.c (build_offset_ref): Build SCOPE_REF with non-null
|
||||
TREE_TYPE for non-dependent names.
|
||||
* typeck.c (build_x_unary_op): Handle non-dependent SCOPE_REF.
|
||||
* pt.c (type_dependent_expression_p): Handle SCOPE_REF with
|
||||
unknown_type_node as its TREE_TYPE.
|
||||
* cxx-pretty_print.c (pp_cxx_unqualified_id): Handle BASELINK.
|
||||
* error.c (dump_decl) <SCOPE_REF case>: Use pp_expression.
|
||||
(dump_expr) <SCOPE_REF case>: Likewise.
|
||||
|
||||
2004-07-21 Kriang Lerdsuwanakij <lerdsuwa@users.sourceforge.net>
|
||||
|
||||
PR c++/16175
|
||||
|
@ -258,7 +258,8 @@ cp/semantics.o: cp/semantics.c $(CXX_TREE_H) $(TM_H) cp/lex.h except.h toplev.h
|
||||
cp/dump.o: cp/dump.c $(CXX_TREE_H) $(TM_H) tree-dump.h
|
||||
cp/optimize.o: cp/optimize.c $(CXX_TREE_H) $(TM_H) rtl.h integrate.h insn-config.h \
|
||||
input.h $(PARAMS_H) debug.h tree-inline.h
|
||||
cp/mangle.o: cp/mangle.c $(CXX_TREE_H) $(TM_H) toplev.h real.h gt-cp-mangle.h $(TM_P_H)
|
||||
cp/mangle.o: cp/mangle.c $(CXX_TREE_H) $(TM_H) toplev.h real.h gt-cp-mangle.h \
|
||||
$(TARGET_H) $(TM_P_H)
|
||||
|
||||
cp/parser.o: cp/parser.c $(CXX_TREE_H) $(TM_H) diagnostic.h gt-cp-parser.h output.h
|
||||
|
||||
|
@ -1,6 +1,6 @@
|
||||
/* Functions related to invoking methods and overloaded functions.
|
||||
Copyright (C) 1987, 1992, 1993, 1994, 1995, 1996, 1997, 1998,
|
||||
1999, 2000, 2001, 2002, 2003, 2004 Free Software Foundation, Inc.
|
||||
1999, 2000, 2001, 2002, 2003, 2004, 2005 Free Software Foundation, Inc.
|
||||
Contributed by Michael Tiemann (tiemann@cygnus.com) and
|
||||
modified by Brendan Kehoe (brendan@cygnus.com).
|
||||
|
||||
@ -86,7 +86,7 @@ static struct z_candidate *add_conv_candidate
|
||||
static struct z_candidate *add_function_candidate
|
||||
(struct z_candidate **, tree, tree, tree, tree, tree, int);
|
||||
static tree implicit_conversion (tree, tree, tree, int);
|
||||
static tree standard_conversion (tree, tree, tree);
|
||||
static tree standard_conversion (tree, tree, tree, int);
|
||||
static tree reference_binding (tree, tree, tree, int);
|
||||
static tree build_conv (enum tree_code, tree, tree);
|
||||
static bool is_subseq (tree, tree);
|
||||
@ -373,6 +373,9 @@ struct z_candidate GTY(()) {
|
||||
#define USER_CONV_CAND(NODE) WRAPPER_ZC (TREE_OPERAND (NODE, 1))
|
||||
#define USER_CONV_FN(NODE) (USER_CONV_CAND (NODE)->fn)
|
||||
|
||||
/* Returns true iff T is a null pointer constant in the sense of
|
||||
[conv.ptr]. */
|
||||
|
||||
bool
|
||||
null_ptr_cst_p (tree t)
|
||||
{
|
||||
@ -380,6 +383,8 @@ null_ptr_cst_p (tree t)
|
||||
|
||||
A null pointer constant is an integral constant expression
|
||||
(_expr.const_) rvalue of integer type that evaluates to zero. */
|
||||
if (DECL_INTEGRAL_CONSTANT_VAR_P (t))
|
||||
t = decl_constant_value (t);
|
||||
if (t == null_node
|
||||
|| (CP_INTEGRAL_TYPE_P (TREE_TYPE (t)) && integer_zerop (t)))
|
||||
return true;
|
||||
@ -449,7 +454,7 @@ strip_top_quals (tree t)
|
||||
also pass the expression EXPR to convert from. */
|
||||
|
||||
static tree
|
||||
standard_conversion (tree to, tree from, tree expr)
|
||||
standard_conversion (tree to, tree from, tree expr, int flags)
|
||||
{
|
||||
enum tree_code fcode, tcode;
|
||||
tree conv;
|
||||
@ -500,7 +505,7 @@ standard_conversion (tree to, tree from, tree expr)
|
||||
the standard conversion sequence to perform componentwise
|
||||
conversion. */
|
||||
tree part_conv = standard_conversion
|
||||
(TREE_TYPE (to), TREE_TYPE (from), NULL_TREE);
|
||||
(TREE_TYPE (to), TREE_TYPE (from), NULL_TREE, flags);
|
||||
|
||||
if (part_conv)
|
||||
{
|
||||
@ -573,6 +578,8 @@ standard_conversion (tree to, tree from, tree expr)
|
||||
TYPE_PTRMEM_POINTED_TO_TYPE (from));
|
||||
conv = build_conv (PMEM_CONV, from, conv);
|
||||
}
|
||||
else if (!same_type_p (fbase, tbase))
|
||||
return NULL;
|
||||
}
|
||||
else if (IS_AGGR_TYPE (TREE_TYPE (from))
|
||||
&& IS_AGGR_TYPE (TREE_TYPE (to))
|
||||
@ -685,7 +692,8 @@ standard_conversion (tree to, tree from, tree expr)
|
||||
&& ((*targetm.vector_opaque_p) (from)
|
||||
|| (*targetm.vector_opaque_p) (to)))
|
||||
return build_conv (STD_CONV, to, conv);
|
||||
else if (IS_AGGR_TYPE (to) && IS_AGGR_TYPE (from)
|
||||
else if (!(flags & LOOKUP_CONSTRUCTOR_CALLABLE)
|
||||
&& IS_AGGR_TYPE (to) && IS_AGGR_TYPE (from)
|
||||
&& is_properly_derived_from (from, to))
|
||||
{
|
||||
if (TREE_CODE (conv) == RVALUE_CONV)
|
||||
@ -1098,7 +1106,7 @@ implicit_conversion (tree to, tree from, tree expr, int flags)
|
||||
if (TREE_CODE (to) == REFERENCE_TYPE)
|
||||
conv = reference_binding (to, from, expr, flags);
|
||||
else
|
||||
conv = standard_conversion (to, from, expr);
|
||||
conv = standard_conversion (to, from, expr, flags);
|
||||
|
||||
if (conv)
|
||||
return conv;
|
||||
@ -2195,10 +2203,18 @@ any_strictly_viable (struct z_candidate *cands)
|
||||
return false;
|
||||
}
|
||||
|
||||
/* OBJ is being used in an expression like "OBJ.f (...)". In other
|
||||
words, it is about to become the "this" pointer for a member
|
||||
function call. Take the address of the object. */
|
||||
|
||||
static tree
|
||||
build_this (tree obj)
|
||||
{
|
||||
/* Fix this to work on non-lvalues. */
|
||||
/* In a template, we are only concerned about the type of the
|
||||
expression, so we can take a shortcut. */
|
||||
if (processing_template_decl)
|
||||
return build_address (obj);
|
||||
|
||||
return build_unary_op (ADDR_EXPR, obj, 0);
|
||||
}
|
||||
|
||||
@ -3270,7 +3286,8 @@ build_conditional_expr (tree arg1, tree arg2, tree arg3)
|
||||
}
|
||||
|
||||
valid_operands:
|
||||
result = fold (build (COND_EXPR, result_type, arg1, arg2, arg3));
|
||||
result = fold_if_not_in_template (build (COND_EXPR, result_type,
|
||||
arg1, arg2, arg3));
|
||||
/* We can't use result_type below, as fold might have returned a
|
||||
throw_expr. */
|
||||
|
||||
@ -3554,20 +3571,6 @@ build_new_op (enum tree_code code, int flags, tree arg1, tree arg2, tree arg3,
|
||||
if (overloaded_p)
|
||||
*overloaded_p = true;
|
||||
|
||||
if (warn_synth
|
||||
&& fnname == ansi_assopname (NOP_EXPR)
|
||||
&& DECL_ARTIFICIAL (cand->fn)
|
||||
&& candidates->next
|
||||
&& ! candidates->next->next)
|
||||
{
|
||||
warning ("using synthesized `%#D' for copy assignment",
|
||||
cand->fn);
|
||||
cp_warning_at (" where cfront would use `%#D'",
|
||||
cand == candidates
|
||||
? candidates->next->fn
|
||||
: candidates->fn);
|
||||
}
|
||||
|
||||
return build_over_call (cand, LOOKUP_NORMAL);
|
||||
}
|
||||
|
||||
@ -3871,6 +3874,7 @@ check_constructor_callable (tree type, tree expr)
|
||||
build_tree_list (NULL_TREE, expr),
|
||||
TYPE_BINFO (type),
|
||||
LOOKUP_NORMAL | LOOKUP_ONLYCONVERTING
|
||||
| LOOKUP_NO_CONVERSION
|
||||
| LOOKUP_CONSTRUCTOR_CALLABLE);
|
||||
}
|
||||
|
||||
@ -6181,6 +6185,8 @@ initialize_reference (tree type, tree expr, tree decl, tree *cleanup)
|
||||
/*fn=*/NULL_TREE, /*argnum=*/0,
|
||||
/*inner=*/-1,
|
||||
/*issue_conversion_warnings=*/true);
|
||||
if (error_operand_p (expr))
|
||||
return error_mark_node;
|
||||
if (!real_lvalue_p (expr))
|
||||
{
|
||||
tree init;
|
||||
|
@ -1,6 +1,7 @@
|
||||
/* Functions related to building classes and their related objects.
|
||||
Copyright (C) 1987, 1992, 1993, 1994, 1995, 1996, 1997, 1998,
|
||||
1999, 2000, 2001, 2002, 2003, 2004 Free Software Foundation, Inc.
|
||||
1999, 2000, 2001, 2002, 2003, 2004, 2005
|
||||
Free Software Foundation, Inc.
|
||||
Contributed by Michael Tiemann (tiemann@cygnus.com)
|
||||
|
||||
This file is part of GCC.
|
||||
@ -1847,6 +1848,36 @@ base_derived_from (tree derived, tree base)
|
||||
return false;
|
||||
}
|
||||
|
||||
typedef struct count_depth_data {
|
||||
/* The depth of the current subobject, with "1" as the depth of the
|
||||
most derived object in the hierarchy. */
|
||||
size_t depth;
|
||||
/* The maximum depth found so far. */
|
||||
size_t max_depth;
|
||||
} count_depth_data;
|
||||
|
||||
/* Called from find_final_overrider via dfs_walk. */
|
||||
|
||||
static tree
|
||||
dfs_depth_post (tree binfo ATTRIBUTE_UNUSED, void *data)
|
||||
{
|
||||
count_depth_data *cd = (count_depth_data *) data;
|
||||
if (cd->depth > cd->max_depth)
|
||||
cd->max_depth = cd->depth;
|
||||
cd->depth--;
|
||||
return NULL_TREE;
|
||||
}
|
||||
|
||||
/* Called from find_final_overrider via dfs_walk. */
|
||||
|
||||
static tree
|
||||
dfs_depth_q (tree derived, int i, void *data)
|
||||
{
|
||||
count_depth_data *cd = (count_depth_data *) data;
|
||||
cd->depth++;
|
||||
return BINFO_BASETYPE (derived, i);
|
||||
}
|
||||
|
||||
typedef struct find_final_overrider_data_s {
|
||||
/* The function for which we are trying to find a final overrider. */
|
||||
tree fn;
|
||||
@ -1856,10 +1887,64 @@ typedef struct find_final_overrider_data_s {
|
||||
tree most_derived_type;
|
||||
/* The candidate overriders. */
|
||||
tree candidates;
|
||||
/* Binfos which inherited virtually on the current path. */
|
||||
tree vpath;
|
||||
/* Each entry in this array is the next-most-derived class for a
|
||||
virtual base class along the current path. */
|
||||
tree *vpath_list;
|
||||
/* A pointer one past the top of the VPATH_LIST. */
|
||||
tree *vpath;
|
||||
} find_final_overrider_data;
|
||||
|
||||
/* Add the overrider along the current path to FFOD->CANDIDATES.
|
||||
Returns true if an overrider was found; false otherwise. */
|
||||
|
||||
static bool
|
||||
dfs_find_final_overrider_1 (tree binfo,
|
||||
tree *vpath,
|
||||
find_final_overrider_data *ffod)
|
||||
{
|
||||
tree method;
|
||||
|
||||
/* If BINFO is not the most derived type, try a more derived class.
|
||||
A definition there will overrider a definition here. */
|
||||
if (!same_type_p (BINFO_TYPE (binfo), ffod->most_derived_type))
|
||||
{
|
||||
tree derived;
|
||||
|
||||
if (TREE_VIA_VIRTUAL (binfo))
|
||||
derived = *--vpath;
|
||||
else
|
||||
derived = BINFO_INHERITANCE_CHAIN (binfo);
|
||||
if (dfs_find_final_overrider_1 (derived, vpath, ffod))
|
||||
return true;
|
||||
}
|
||||
|
||||
method = look_for_overrides_here (BINFO_TYPE (binfo), ffod->fn);
|
||||
if (method)
|
||||
{
|
||||
tree *candidate = &ffod->candidates;
|
||||
|
||||
/* Remove any candidates overridden by this new function. */
|
||||
while (*candidate)
|
||||
{
|
||||
/* If *CANDIDATE overrides METHOD, then METHOD
|
||||
cannot override anything else on the list. */
|
||||
if (base_derived_from (TREE_VALUE (*candidate), binfo))
|
||||
return true;
|
||||
/* If METHOD overrides *CANDIDATE, remove *CANDIDATE. */
|
||||
if (base_derived_from (binfo, TREE_VALUE (*candidate)))
|
||||
*candidate = TREE_CHAIN (*candidate);
|
||||
else
|
||||
candidate = &TREE_CHAIN (*candidate);
|
||||
}
|
||||
|
||||
/* Add the new function. */
|
||||
ffod->candidates = tree_cons (method, binfo, ffod->candidates);
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
/* Called from find_final_overrider via dfs_walk. */
|
||||
|
||||
static tree
|
||||
@ -1868,57 +1953,7 @@ dfs_find_final_overrider (tree binfo, void* data)
|
||||
find_final_overrider_data *ffod = (find_final_overrider_data *) data;
|
||||
|
||||
if (binfo == ffod->declaring_base)
|
||||
{
|
||||
/* We've found a path to the declaring base. Walk the path from
|
||||
derived to base, looking for an overrider for FN. */
|
||||
tree path, probe, vpath;
|
||||
|
||||
/* Build the path, using the inheritance chain and record of
|
||||
virtual inheritance. */
|
||||
for (path = NULL_TREE, probe = binfo, vpath = ffod->vpath;;)
|
||||
{
|
||||
path = tree_cons (NULL_TREE, probe, path);
|
||||
if (same_type_p (BINFO_TYPE (probe), ffod->most_derived_type))
|
||||
break;
|
||||
if (TREE_VIA_VIRTUAL (probe))
|
||||
{
|
||||
probe = TREE_VALUE (vpath);
|
||||
vpath = TREE_CHAIN (vpath);
|
||||
}
|
||||
else
|
||||
probe = BINFO_INHERITANCE_CHAIN (probe);
|
||||
}
|
||||
/* Now walk path, looking for overrides. */
|
||||
for (; path; path = TREE_CHAIN (path))
|
||||
{
|
||||
tree method = look_for_overrides_here
|
||||
(BINFO_TYPE (TREE_VALUE (path)), ffod->fn);
|
||||
|
||||
if (method)
|
||||
{
|
||||
tree *candidate = &ffod->candidates;
|
||||
path = TREE_VALUE (path);
|
||||
|
||||
/* Remove any candidates overridden by this new function. */
|
||||
while (*candidate)
|
||||
{
|
||||
/* If *CANDIDATE overrides METHOD, then METHOD
|
||||
cannot override anything else on the list. */
|
||||
if (base_derived_from (TREE_VALUE (*candidate), path))
|
||||
return NULL_TREE;
|
||||
/* If METHOD overrides *CANDIDATE, remove *CANDIDATE. */
|
||||
if (base_derived_from (path, TREE_VALUE (*candidate)))
|
||||
*candidate = TREE_CHAIN (*candidate);
|
||||
else
|
||||
candidate = &TREE_CHAIN (*candidate);
|
||||
}
|
||||
|
||||
/* Add the new function. */
|
||||
ffod->candidates = tree_cons (method, path, ffod->candidates);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
dfs_find_final_overrider_1 (binfo, ffod->vpath, ffod);
|
||||
|
||||
return NULL_TREE;
|
||||
}
|
||||
@ -1930,7 +1965,7 @@ dfs_find_final_overrider_q (tree derived, int ix, void *data)
|
||||
find_final_overrider_data *ffod = (find_final_overrider_data *) data;
|
||||
|
||||
if (TREE_VIA_VIRTUAL (binfo))
|
||||
ffod->vpath = tree_cons (NULL_TREE, derived, ffod->vpath);
|
||||
*ffod->vpath++ = derived;
|
||||
|
||||
return binfo;
|
||||
}
|
||||
@ -1940,8 +1975,8 @@ dfs_find_final_overrider_post (tree binfo, void *data)
|
||||
{
|
||||
find_final_overrider_data *ffod = (find_final_overrider_data *) data;
|
||||
|
||||
if (TREE_VIA_VIRTUAL (binfo) && TREE_CHAIN (ffod->vpath))
|
||||
ffod->vpath = TREE_CHAIN (ffod->vpath);
|
||||
if (TREE_VIA_VIRTUAL (binfo))
|
||||
ffod->vpath--;
|
||||
|
||||
return NULL_TREE;
|
||||
}
|
||||
@ -1955,6 +1990,7 @@ static tree
|
||||
find_final_overrider (tree derived, tree binfo, tree fn)
|
||||
{
|
||||
find_final_overrider_data ffod;
|
||||
count_depth_data cd;
|
||||
|
||||
/* Getting this right is a little tricky. This is valid:
|
||||
|
||||
@ -1976,12 +2012,18 @@ find_final_overrider (tree derived, tree binfo, tree fn)
|
||||
different overriders along any two, then there is a problem. */
|
||||
if (DECL_THUNK_P (fn))
|
||||
fn = THUNK_TARGET (fn);
|
||||
|
||||
|
||||
/* Determine the depth of the hierarchy. */
|
||||
cd.depth = 0;
|
||||
cd.max_depth = 0;
|
||||
dfs_walk (derived, dfs_depth_post, dfs_depth_q, &cd);
|
||||
|
||||
ffod.fn = fn;
|
||||
ffod.declaring_base = binfo;
|
||||
ffod.most_derived_type = BINFO_TYPE (derived);
|
||||
ffod.candidates = NULL_TREE;
|
||||
ffod.vpath = NULL_TREE;
|
||||
ffod.vpath_list = (tree *) xcalloc (cd.max_depth, sizeof (tree));
|
||||
ffod.vpath = ffod.vpath_list;
|
||||
|
||||
dfs_walk_real (derived,
|
||||
dfs_find_final_overrider,
|
||||
@ -1989,6 +2031,8 @@ find_final_overrider (tree derived, tree binfo, tree fn)
|
||||
dfs_find_final_overrider_q,
|
||||
&ffod);
|
||||
|
||||
free (ffod.vpath_list);
|
||||
|
||||
/* If there was no winner, issue an error message. */
|
||||
if (!ffod.candidates || TREE_CHAIN (ffod.candidates))
|
||||
{
|
||||
@ -2072,6 +2116,9 @@ update_vtable_entry_for_fn (tree t, tree binfo, tree fn, tree* virtuals,
|
||||
also be converting to the return type of FN, we have to
|
||||
combine the two conversions here. */
|
||||
tree fixed_offset, virtual_offset;
|
||||
|
||||
over_return = TREE_TYPE (over_return);
|
||||
base_return = TREE_TYPE (base_return);
|
||||
|
||||
if (DECL_THUNK_P (fn))
|
||||
{
|
||||
@ -2089,32 +2136,51 @@ update_vtable_entry_for_fn (tree t, tree binfo, tree fn, tree* virtuals,
|
||||
virtual_offset =
|
||||
TREE_VALUE (purpose_member
|
||||
(BINFO_TYPE (virtual_offset),
|
||||
CLASSTYPE_VBASECLASSES (TREE_TYPE (over_return))));
|
||||
else if (!same_type_p (TREE_TYPE (over_return),
|
||||
TREE_TYPE (base_return)))
|
||||
CLASSTYPE_VBASECLASSES (over_return)));
|
||||
else if (!same_type_ignoring_top_level_qualifiers_p
|
||||
(over_return, base_return))
|
||||
{
|
||||
/* There was no existing virtual thunk (which takes
|
||||
precedence). */
|
||||
tree thunk_binfo;
|
||||
base_kind kind;
|
||||
|
||||
thunk_binfo = lookup_base (TREE_TYPE (over_return),
|
||||
TREE_TYPE (base_return),
|
||||
ba_check | ba_quiet, &kind);
|
||||
/* There was no existing virtual thunk (which takes
|
||||
precedence). So find the binfo of the base function's
|
||||
return type within the overriding function's return type.
|
||||
We cannot call lookup base here, because we're inside a
|
||||
dfs_walk, and will therefore clobber the BINFO_MARKED
|
||||
flags. Fortunately we know the covariancy is valid (it
|
||||
has already been checked), so we can just iterate along
|
||||
the binfos, which have been chained in inheritance graph
|
||||
order. Of course it is lame that we have to repeat the
|
||||
search here anyway -- we should really be caching pieces
|
||||
of the vtable and avoiding this repeated work. */
|
||||
tree thunk_binfo, base_binfo;
|
||||
|
||||
if (thunk_binfo && (kind == bk_via_virtual
|
||||
|| !BINFO_OFFSET_ZEROP (thunk_binfo)))
|
||||
/* Find the base binfo within the overriding function's
|
||||
return type. We will always find a thunk_binfo, except
|
||||
when the covariancy is invalid (which we will have
|
||||
already diagnosed). */
|
||||
for (base_binfo = TYPE_BINFO (base_return),
|
||||
thunk_binfo = TYPE_BINFO (over_return);
|
||||
thunk_binfo;
|
||||
thunk_binfo = TREE_CHAIN (thunk_binfo))
|
||||
if (same_type_p (BINFO_TYPE (thunk_binfo),
|
||||
BINFO_TYPE (base_binfo)))
|
||||
break;
|
||||
|
||||
/* See if virtual inheritance is involved. */
|
||||
for (virtual_offset = thunk_binfo;
|
||||
virtual_offset;
|
||||
virtual_offset = BINFO_INHERITANCE_CHAIN (virtual_offset))
|
||||
if (TREE_VIA_VIRTUAL (virtual_offset))
|
||||
break;
|
||||
|
||||
if (virtual_offset
|
||||
|| (thunk_binfo && !BINFO_OFFSET_ZEROP (thunk_binfo)))
|
||||
{
|
||||
tree offset = convert (ssizetype, BINFO_OFFSET (thunk_binfo));
|
||||
|
||||
if (kind == bk_via_virtual)
|
||||
if (virtual_offset)
|
||||
{
|
||||
/* We convert via virtual base. Find the virtual
|
||||
base and adjust the fixed offset to be from there. */
|
||||
while (!TREE_VIA_VIRTUAL (thunk_binfo))
|
||||
thunk_binfo = BINFO_INHERITANCE_CHAIN (thunk_binfo);
|
||||
|
||||
virtual_offset = thunk_binfo;
|
||||
/* We convert via virtual base. Adjust the fixed
|
||||
offset to be from there. */
|
||||
offset = size_diffop
|
||||
(offset, convert
|
||||
(ssizetype, BINFO_OFFSET (virtual_offset)));
|
||||
@ -5174,6 +5240,7 @@ finish_struct (tree t, tree attributes)
|
||||
{
|
||||
finish_struct_methods (t);
|
||||
TYPE_SIZE (t) = bitsize_zero_node;
|
||||
TYPE_SIZE_UNIT (t) = size_zero_node;
|
||||
}
|
||||
else
|
||||
finish_struct_1 (t);
|
||||
|
Some files were not shown because too many files have changed in this diff Show More
Loading…
x
Reference in New Issue
Block a user