summaryrefslogtreecommitdiff
path: root/gcc
diff options
context:
space:
mode:
Diffstat (limited to 'gcc')
-rw-r--r--gcc/ChangeLog9
-rw-r--r--gcc/emit-rtl.c8
-rw-r--r--gcc/expr.c41
-rw-r--r--gcc/tree.h8
4 files changed, 46 insertions, 20 deletions
diff --git a/gcc/ChangeLog b/gcc/ChangeLog
index 5ef917e3493..06c94373b0d 100644
--- a/gcc/ChangeLog
+++ b/gcc/ChangeLog
@@ -1,5 +1,14 @@
Sun Nov 18 14:13:52 2001 Richard Kenner <kenner@vlsi1.ultra.nyu.edu>
+ * tree.h (TYPE_ALIGN_OK): New flag.
+ * emit-rtl.c (set_mem_attributes): Handle it.
+ * expr.c (emit_single_push_insn): Only set to alias set 0 if
+ doing sibcall optimization.
+ (expand_expr, case COMPONENT_REF): Call set_mem_attributes on case
+ when make temporary.
+ (expand_expr, case CONVERT_EXPR): Simplify convert-to-union case.
+ (expand_expr, case ADDR_EXPR): Abort if TYPE_ALIGN_OK and need copy.
+
* sdbout.c (sdbout_symbol): Avoid warning due to &DECL_RTL.
2001-11-18 Joseph S. Myers <jsm28@cam.ac.uk>
diff --git a/gcc/emit-rtl.c b/gcc/emit-rtl.c
index 9ad98f02cb4..ec2e4f372e1 100644
--- a/gcc/emit-rtl.c
+++ b/gcc/emit-rtl.c
@@ -1699,10 +1699,10 @@ set_mem_attributes (ref, t, objectp)
if ((objectp || DECL_P (t)) && ! AGGREGATE_TYPE_P (type))
MEM_SCALAR_P (ref) = 1;
- /* We can set the alignment from the type if we are makign an object or
- if this is an INDIRECT_REF. */
- if (objectp || TREE_CODE (t) == INDIRECT_REF)
- align = TYPE_ALIGN (type);
+ /* We can set the alignment from the type if we are making an object,
+ this is an INDIRECT_REF, or if TYPE_ALIGN_OK. */
+ if (objectp || TREE_CODE (t) == INDIRECT_REF || TYPE_ALIGN_OK (type))
+ align = MAX (align, TYPE_ALIGN (type));
/* If the size is known, we can set that. */
if (TYPE_SIZE_UNIT (type) && host_integerp (TYPE_SIZE_UNIT (type), 1))
diff --git a/gcc/expr.c b/gcc/expr.c
index 92397ee4064..5d933b29543 100644
--- a/gcc/expr.c
+++ b/gcc/expr.c
@@ -3199,11 +3199,13 @@ emit_single_push_insn (mode, x, type)
if (type != 0)
{
set_mem_attributes (dest, type, 1);
- /* Function incoming arguments may overlap with sibling call
- outgoing arguments and we cannot allow reordering of reads
- from function arguments with stores to outgoing arguments
- of sibling calls. */
- set_mem_alias_set (dest, 0);
+
+ if (flag_optimize_sibling_calls)
+ /* Function incoming arguments may overlap with sibling call
+ outgoing arguments and we cannot allow reordering of reads
+ from function arguments with stores to outgoing arguments
+ of sibling calls. */
+ set_mem_alias_set (dest, 0);
}
emit_move_insn (dest, x);
}
@@ -7180,13 +7182,14 @@ expand_expr (exp, target, tmode, modifier)
if (mode == BLKmode)
{
- tree nt = build_qualified_type (type_for_mode (ext_mode, 0),
- TYPE_QUAL_CONST);
- rtx new = assign_temp (nt, 0, 1, 1);
+ rtx new = assign_temp (build_qualified_type
+ (type_for_mode (ext_mode, 0),
+ TYPE_QUAL_CONST), 0, 1, 1);
emit_move_insn (new, op0);
op0 = copy_rtx (new);
PUT_MODE (op0, BLKmode);
+ set_mem_attributes (op0, exp, 1);
}
return op0;
@@ -7423,14 +7426,17 @@ expand_expr (exp, target, tmode, modifier)
{
tree valtype = TREE_TYPE (TREE_OPERAND (exp, 0));
- /* If both input and output are BLKmode, this conversion
- isn't actually doing anything unless we need to make the
- alignment stricter. */
- if (mode == BLKmode && TYPE_MODE (valtype) == BLKmode
- && (TYPE_ALIGN (type) <= TYPE_ALIGN (valtype)
- || TYPE_ALIGN (type) >= BIGGEST_ALIGNMENT))
- return expand_expr (TREE_OPERAND (exp, 0), target, tmode,
- modifier);
+ /* If both input and output are BLKmode, this conversion isn't doing
+ anything except possibly changing memory attribute. */
+ if (mode == BLKmode && TYPE_MODE (valtype) == BLKmode)
+ {
+ rtx result = expand_expr (TREE_OPERAND (exp, 0), target, tmode,
+ modifier);
+
+ result = copy_rtx (result);
+ set_mem_attributes (result, exp, 0);
+ return result;
+ }
if (target == 0)
target = assign_temp (type, 0, 1, 1);
@@ -8673,6 +8679,9 @@ expand_expr (exp, target, tmode, modifier)
(TYPE_QUALS (inner_type)
| TYPE_QUAL_CONST)));
+ if (TYPE_ALIGN_OK (inner_type))
+ abort ();
+
emit_block_move (new, op0, expr_size (TREE_OPERAND (exp, 0)));
op0 = new;
}
diff --git a/gcc/tree.h b/gcc/tree.h
index 98ba6e59792..9c45fb851ad 100644
--- a/gcc/tree.h
+++ b/gcc/tree.h
@@ -596,6 +596,14 @@ extern void tree_class_check_failed PARAMS ((const tree, int,
an exception. In a CALL_EXPR, nonzero means the call cannot throw. */
#define TREE_NOTHROW(NODE) ((NODE)->common.nothrow_flag)
+/* In a type, nonzero means that all objects of the type are guaranteed by the
+ language or front-end to be properly aligned, so we can indicate that a MEM
+ of this type is aligned at least to the alignment of the type, even if it
+ doesn't appear that it is. We see this, for example, in object-oriented
+ languages where a tag field may show this is an object of a more-aligned
+ variant of the more generic type. */
+#define TYPE_ALIGN_OK(NODE) (TYPE_CHECK (NODE)->common.nothrow_flag)
+
/* Used in classes in C++. */
#define TREE_PRIVATE(NODE) ((NODE)->common.private_flag)
/* Used in classes in C++.