aboutsummaryrefslogtreecommitdiffstats
path: root/gcc-4.8/gcc/ada/gcc-interface
diff options
context:
space:
mode:
Diffstat (limited to 'gcc-4.8/gcc/ada/gcc-interface')
-rw-r--r--gcc-4.8/gcc/ada/gcc-interface/Make-lang.in2
-rw-r--r--gcc-4.8/gcc/ada/gcc-interface/Makefile.in8
-rw-r--r--gcc-4.8/gcc/ada/gcc-interface/cuintp.c21
-rw-r--r--gcc-4.8/gcc/ada/gcc-interface/gigi.h2
-rw-r--r--gcc-4.8/gcc/ada/gcc-interface/misc.c25
-rw-r--r--gcc-4.8/gcc/ada/gcc-interface/utils.c128
6 files changed, 100 insertions, 86 deletions
diff --git a/gcc-4.8/gcc/ada/gcc-interface/Make-lang.in b/gcc-4.8/gcc/ada/gcc-interface/Make-lang.in
index 57f90090d..e1d3ed6eb 100644
--- a/gcc-4.8/gcc/ada/gcc-interface/Make-lang.in
+++ b/gcc-4.8/gcc/ada/gcc-interface/Make-lang.in
@@ -625,7 +625,7 @@ ada.tags: force
ada/doctools/xgnatugn$(build_exeext): ada/xgnatugn.adb
-$(MKDIR) ada/doctools
$(CP) $^ ada/doctools
- cd ada/doctools && $(GNATMAKE) -q xgnatugn
+ cd ada/doctools && gnatmake -q xgnatugn
# Note that doc/gnat_ugn.texi and doc/projects.texi do not depend on
# xgnatugn being built so we can distribute a pregenerated doc/gnat_ugn.info
diff --git a/gcc-4.8/gcc/ada/gcc-interface/Makefile.in b/gcc-4.8/gcc/ada/gcc-interface/Makefile.in
index 0ddde7294..ee610f789 100644
--- a/gcc-4.8/gcc/ada/gcc-interface/Makefile.in
+++ b/gcc-4.8/gcc/ada/gcc-interface/Makefile.in
@@ -2397,7 +2397,7 @@ TOOLS_FLAGS_TO_PASS= \
"GNATLINK=$(GNATLINK)" \
"GNATBIND=$(GNATBIND)"
-GCC_LINK=$(CC) $(GCC_LINK_FLAGS) $(ADA_INCLUDES)
+GCC_LINK=$(CC) $(GCC_LINK_FLAGS) $(ADA_INCLUDES) $(LDFLAGS)
# Build directory for the tools. Let's copy the target-dependent
# sources using the same mechanism as for gnatlib. The other sources are
@@ -2519,12 +2519,10 @@ gnatlink-re: ../stamp-tools link.o targext.o gnatmake-re
# Likewise for the tools
../../gnatmake$(exeext): $(P) b_gnatm.o link.o targext.o $(GNATMAKE_OBJS)
- $(GCC_LINK) $(ALL_CFLAGS) $(LDFLAGS) -o $@ b_gnatm.o $(GNATMAKE_OBJS) \
- $(TOOLS_LIBS)
+ +$(GCC_LINK) $(ALL_CFLAGS) -o $@ b_gnatm.o $(GNATMAKE_OBJS) $(TOOLS_LIBS)
../../gnatlink$(exeext): $(P) b_gnatl.o link.o targext.o $(GNATLINK_OBJS)
- $(GCC_LINK) $(ALL_CFLAGS) $(LDFLAGS) -o $@ b_gnatl.o $(GNATLINK_OBJS) \
- $(TOOLS_LIBS)
+ +$(GCC_LINK) $(ALL_CFLAGS) -o $@ b_gnatl.o $(GNATLINK_OBJS) $(TOOLS_LIBS)
../stamp-gnatlib-$(RTSDIR):
@if [ ! -f stamp-gnatlib-$(RTSDIR) ] ; \
diff --git a/gcc-4.8/gcc/ada/gcc-interface/cuintp.c b/gcc-4.8/gcc/ada/gcc-interface/cuintp.c
index e077d9ce0..f4d75eca2 100644
--- a/gcc-4.8/gcc/ada/gcc-interface/cuintp.c
+++ b/gcc-4.8/gcc/ada/gcc-interface/cuintp.c
@@ -6,7 +6,7 @@
* *
* C Implementation File *
* *
- * Copyright (C) 1992-2012, Free Software Foundation, Inc. *
+ * Copyright (C) 1992-2014, Free Software Foundation, Inc. *
* *
* GNAT is free software; you can redistribute it and/or modify it under *
* terms of the GNU General Public License as published by the Free Soft- *
@@ -59,8 +59,8 @@
static tree
build_cst_from_int (tree type, HOST_WIDE_INT low)
{
- if (TREE_CODE (type) == REAL_TYPE)
- return convert (type, build_int_cst (NULL_TREE, low));
+ if (SCALAR_FLOAT_TYPE_P (type))
+ return convert (type, build_int_cst (gnat_type_for_size (32, 0), low));
else
return build_int_cst_type (type, low);
}
@@ -99,19 +99,12 @@ UI_To_gnu (Uint Input, tree type)
gcc_assert (Length > 0);
/* The computations we perform below always require a type at least as
- large as an integer not to overflow. REAL types are always fine, but
+ large as an integer not to overflow. FP types are always fine, but
INTEGER or ENUMERAL types we are handed may be too short. We use a
base integer type node for the computations in this case and will
- convert the final result back to the incoming type later on.
- The base integer precision must be superior than 16. */
-
- if (TREE_CODE (comp_type) != REAL_TYPE
- && TYPE_PRECISION (comp_type)
- < TYPE_PRECISION (long_integer_type_node))
- {
- comp_type = long_integer_type_node;
- gcc_assert (TYPE_PRECISION (comp_type) > 16);
- }
+ convert the final result back to the incoming type later on. */
+ if (!SCALAR_FLOAT_TYPE_P (comp_type) && TYPE_PRECISION (comp_type) < 32)
+ comp_type = gnat_type_for_size (32, 0);
gnu_base = build_cst_from_int (comp_type, Base);
diff --git a/gcc-4.8/gcc/ada/gcc-interface/gigi.h b/gcc-4.8/gcc/ada/gcc-interface/gigi.h
index de1c7e86d..c0db89bda 100644
--- a/gcc-4.8/gcc/ada/gcc-interface/gigi.h
+++ b/gcc-4.8/gcc/ada/gcc-interface/gigi.h
@@ -1014,7 +1014,7 @@ extern Nat get_target_double_scalar_alignment (void);
/* This function is called by the front-end to enumerate all the supported
modes for the machine, as well as some predefined C types. */
extern void enumerate_modes (void (*f) (const char *, int, int, int, int, int,
- int));
+ int, int));
#ifdef __cplusplus
}
diff --git a/gcc-4.8/gcc/ada/gcc-interface/misc.c b/gcc-4.8/gcc/ada/gcc-interface/misc.c
index 2fd2743bb..83620487b 100644
--- a/gcc-4.8/gcc/ada/gcc-interface/misc.c
+++ b/gcc-4.8/gcc/ada/gcc-interface/misc.c
@@ -648,7 +648,7 @@ must_pass_by_ref (tree gnu_type)
/* This function is called by the front-end to enumerate all the supported
modes for the machine, as well as some predefined C types. F is a function
which is called back with the parameters as listed below, first a string,
- then six ints. The name is any arbitrary null-terminated string and has
+ then seven ints. The name is any arbitrary null-terminated string and has
no particular significance, except for the case of predefined C types, where
it should be the name of the C type. For integer types, only signed types
should be listed, unsigned versions are assumed. The order of types should
@@ -664,11 +664,12 @@ must_pass_by_ref (tree gnu_type)
COMPLEX_P nonzero is this represents a complex mode
COUNT count of number of items, nonzero for vector mode
FLOAT_REP Float_Rep_Kind for FP, otherwise undefined
- SIZE number of bits used to store data
+ PRECISION number of bits used to store data
+ SIZE number of bits occupied by the mode
ALIGN number of bits to which mode is aligned. */
void
-enumerate_modes (void (*f) (const char *, int, int, int, int, int, int))
+enumerate_modes (void (*f) (const char *, int, int, int, int, int, int, int))
{
const tree c_types[]
= { float_type_node, double_type_node, long_double_type_node };
@@ -742,28 +743,26 @@ enumerate_modes (void (*f) (const char *, int, int, int, int, int, int))
/* First register any C types for this mode that the front end
may need to know about, unless the mode should be skipped. */
-
- if (!skip_p)
+ if (!skip_p && !vector_p)
for (nameloop = 0; nameloop < ARRAY_SIZE (c_types); nameloop++)
{
- tree typ = c_types[nameloop];
- const char *nam = c_names[nameloop];
+ tree type = c_types[nameloop];
+ const char *name = c_names[nameloop];
- if (TYPE_MODE (typ) == i)
+ if (TYPE_MODE (type) == i)
{
- f (nam, digs, complex_p,
- vector_p ? GET_MODE_NUNITS (i) : 0, float_rep,
- TYPE_PRECISION (typ), TYPE_ALIGN (typ));
+ f (name, digs, complex_p, 0, float_rep, TYPE_PRECISION (type),
+ TREE_INT_CST_LOW (TYPE_SIZE (type)), TYPE_ALIGN (type));
skip_p = true;
}
}
/* If no predefined C types were found, register the mode itself. */
-
if (!skip_p)
f (GET_MODE_NAME (i), digs, complex_p,
vector_p ? GET_MODE_NUNITS (i) : 0, float_rep,
- GET_MODE_PRECISION (i), GET_MODE_ALIGNMENT (i));
+ GET_MODE_PRECISION (i), GET_MODE_BITSIZE (i),
+ GET_MODE_ALIGNMENT (i));
}
}
diff --git a/gcc-4.8/gcc/ada/gcc-interface/utils.c b/gcc-4.8/gcc/ada/gcc-interface/utils.c
index c5cee7a00..b90922b23 100644
--- a/gcc-4.8/gcc/ada/gcc-interface/utils.c
+++ b/gcc-4.8/gcc/ada/gcc-interface/utils.c
@@ -232,6 +232,7 @@ static tree compute_related_constant (tree, tree);
static tree split_plus (tree, tree *);
static tree float_type_for_precision (int, enum machine_mode);
static tree convert_to_fat_pointer (tree, tree);
+static unsigned int scale_by_factor_of (tree, unsigned int);
static bool potential_alignment_gap (tree, tree, tree);
static void process_attributes (tree, struct attrib *);
@@ -532,6 +533,22 @@ gnat_zaplevel (void)
free_binding_level = level;
}
+/* Set the context of TYPE and its parallel types (if any) to CONTEXT. */
+
+static void
+gnat_set_type_context (tree type, tree context)
+{
+ tree decl = TYPE_STUB_DECL (type);
+
+ TYPE_CONTEXT (type) = context;
+
+ while (decl && DECL_PARALLEL_TYPE (decl))
+ {
+ TYPE_CONTEXT (DECL_PARALLEL_TYPE (decl)) = context;
+ decl = TYPE_STUB_DECL (DECL_PARALLEL_TYPE (decl));
+ }
+}
+
/* Record DECL as belonging to the current lexical scope and use GNAT_NODE
for location information and flag propagation. */
@@ -613,7 +630,7 @@ gnat_pushdecl (tree decl, Node_Id gnat_node)
if (TREE_CODE (t) == POINTER_TYPE)
TYPE_NEXT_PTR_TO (t) = tt;
TYPE_NAME (tt) = DECL_NAME (decl);
- TYPE_CONTEXT (tt) = DECL_CONTEXT (decl);
+ gnat_set_type_context (tt, DECL_CONTEXT (decl));
TYPE_STUB_DECL (tt) = TYPE_STUB_DECL (t);
DECL_ORIGINAL_TYPE (decl) = tt;
}
@@ -623,7 +640,7 @@ gnat_pushdecl (tree decl, Node_Id gnat_node)
/* We need a variant for the placeholder machinery to work. */
tree tt = build_variant_type_copy (t);
TYPE_NAME (tt) = decl;
- TYPE_CONTEXT (tt) = DECL_CONTEXT (decl);
+ gnat_set_type_context (tt, DECL_CONTEXT (decl));
TREE_USED (tt) = TREE_USED (t);
TREE_TYPE (decl) = tt;
if (DECL_ORIGINAL_TYPE (TYPE_NAME (t)))
@@ -645,7 +662,7 @@ gnat_pushdecl (tree decl, Node_Id gnat_node)
if (!(TYPE_NAME (t) && TREE_CODE (TYPE_NAME (t)) == TYPE_DECL))
{
TYPE_NAME (t) = decl;
- TYPE_CONTEXT (t) = DECL_CONTEXT (decl);
+ gnat_set_type_context (t, DECL_CONTEXT (decl));
}
}
}
@@ -1692,18 +1709,21 @@ rest_of_record_type_compilation (tree record_type)
TYPE_SIZE_UNIT (new_record_type)
= size_int (TYPE_ALIGN (record_type) / BITS_PER_UNIT);
- /* Now scan all the fields, replacing each field with a new
- field corresponding to the new encoding. */
+ /* Now scan all the fields, replacing each field with a new field
+ corresponding to the new encoding. */
for (old_field = TYPE_FIELDS (record_type); old_field;
old_field = DECL_CHAIN (old_field))
{
tree field_type = TREE_TYPE (old_field);
tree field_name = DECL_NAME (old_field);
- tree new_field;
tree curpos = bit_position (old_field);
+ tree pos, new_field;
bool var = false;
unsigned int align = 0;
- tree pos;
+
+ /* We're going to do some pattern matching below so remove as many
+ conversions as possible. */
+ curpos = remove_conversions (curpos, true);
/* See how the position was modified from the last position.
@@ -1711,74 +1731,52 @@ rest_of_record_type_compilation (tree record_type)
to the last position or the last position was rounded to
a boundary and they something was added. Check for the
first case first. If not, see if there is any evidence
- of rounding. If so, round the last position and try
- again.
+ of rounding. If so, round the last position and retry.
If this is a union, the position can be taken as zero. */
-
- /* Some computations depend on the shape of the position expression,
- so strip conversions to make sure it's exposed. */
- curpos = remove_conversions (curpos, true);
-
if (TREE_CODE (new_record_type) == UNION_TYPE)
- pos = bitsize_zero_node, align = 0;
+ pos = bitsize_zero_node;
else
pos = compute_related_constant (curpos, last_pos);
- if (!pos && TREE_CODE (curpos) == MULT_EXPR
+ if (!pos
+ && TREE_CODE (curpos) == MULT_EXPR
&& host_integerp (TREE_OPERAND (curpos, 1), 1))
{
tree offset = TREE_OPERAND (curpos, 0);
align = tree_low_cst (TREE_OPERAND (curpos, 1), 1);
-
- /* An offset which is a bitwise AND with a mask increases the
- alignment according to the number of trailing zeros. */
- offset = remove_conversions (offset, true);
- if (TREE_CODE (offset) == BIT_AND_EXPR
- && TREE_CODE (TREE_OPERAND (offset, 1)) == INTEGER_CST)
- {
- unsigned HOST_WIDE_INT mask
- = TREE_INT_CST_LOW (TREE_OPERAND (offset, 1));
- unsigned int i;
-
- for (i = 0; i < HOST_BITS_PER_WIDE_INT; i++)
- {
- if (mask & 1)
- break;
- mask >>= 1;
- align *= 2;
- }
- }
-
- pos = compute_related_constant (curpos,
- round_up (last_pos, align));
+ align = scale_by_factor_of (offset, align);
+ last_pos = round_up (last_pos, align);
+ pos = compute_related_constant (curpos, last_pos);
}
- else if (!pos && TREE_CODE (curpos) == PLUS_EXPR
- && TREE_CODE (TREE_OPERAND (curpos, 1)) == INTEGER_CST
+ else if (!pos
+ && TREE_CODE (curpos) == PLUS_EXPR
+ && host_integerp (TREE_OPERAND (curpos, 1), 1)
&& TREE_CODE (TREE_OPERAND (curpos, 0)) == MULT_EXPR
- && host_integerp (TREE_OPERAND
- (TREE_OPERAND (curpos, 0), 1),
- 1))
+ && host_integerp
+ (TREE_OPERAND (TREE_OPERAND (curpos, 0), 1), 1))
{
+ tree offset = TREE_OPERAND (TREE_OPERAND (curpos, 0), 0);
+ unsigned HOST_WIDE_INT addend
+ = tree_low_cst (TREE_OPERAND (curpos, 1), 1);
align
- = tree_low_cst
- (TREE_OPERAND (TREE_OPERAND (curpos, 0), 1), 1);
- pos = compute_related_constant (curpos,
- round_up (last_pos, align));
+ = tree_low_cst (TREE_OPERAND (TREE_OPERAND (curpos, 0), 1), 1);
+ align = scale_by_factor_of (offset, align);
+ align = MIN (align, addend & -addend);
+ last_pos = round_up (last_pos, align);
+ pos = compute_related_constant (curpos, last_pos);
}
- else if (potential_alignment_gap (prev_old_field, old_field,
- pos))
+ else if (potential_alignment_gap (prev_old_field, old_field, pos))
{
align = TYPE_ALIGN (field_type);
- pos = compute_related_constant (curpos,
- round_up (last_pos, align));
+ last_pos = round_up (last_pos, align);
+ pos = compute_related_constant (curpos, last_pos);
}
/* If we can't compute a position, set it to zero.
??? We really should abort here, but it's too much work
to get this correct for all cases. */
-
if (!pos)
pos = bitsize_zero_node;
@@ -2553,6 +2551,32 @@ value_factor_p (tree value, HOST_WIDE_INT factor)
return false;
}
+/* Return VALUE scaled by the biggest power-of-2 factor of EXPR. */
+
+static unsigned int
+scale_by_factor_of (tree expr, unsigned int value)
+{
+ expr = remove_conversions (expr, true);
+
+ /* An expression which is a bitwise AND with a mask has a power-of-2 factor
+ corresponding to the number of trailing zeros of the mask. */
+ if (TREE_CODE (expr) == BIT_AND_EXPR
+ && TREE_CODE (TREE_OPERAND (expr, 1)) == INTEGER_CST)
+ {
+ unsigned HOST_WIDE_INT mask = TREE_INT_CST_LOW (TREE_OPERAND (expr, 1));
+ unsigned int i = 0;
+
+ while ((mask & 1) == 0 && i < HOST_BITS_PER_WIDE_INT)
+ {
+ mask >>= 1;
+ value *= 2;
+ i++;
+ }
+ }
+
+ return value;
+}
+
/* Given two consecutive field decls PREV_FIELD and CURR_FIELD, return true
unless we can prove these 2 fields are laid out in such a way that no gap
exist between the end of PREV_FIELD and the beginning of CURR_FIELD. OFFSET