diff options
author | jakub <jakub@138bc75d-0d04-0410-961f-82ee72b054a4> | 2001-02-14 07:57:49 +0000 |
---|---|---|
committer | jakub <jakub@138bc75d-0d04-0410-961f-82ee72b054a4> | 2001-02-14 07:57:49 +0000 |
commit | fe1302cffc9f963afbea472bb4ac9fce52d759a0 (patch) | |
tree | 1998ac8deccf251adebd1cb63da29b3285bdd37f | |
parent | d4fd22f2e3fbdf417a6e7e8230bfa34a04d75b31 (diff) | |
download | ppe42-gcc-fe1302cffc9f963afbea472bb4ac9fce52d759a0.tar.gz ppe42-gcc-fe1302cffc9f963afbea472bb4ac9fce52d759a0.zip |
* stor-layout.c (is_pending_size, put_pending_size): New functions.
(variable_size): Call put_pending_size.
* tree.h (is_pending_size, put_pending_size): Add prototypes.
* fold-const.c (extract_muldiv): If SAVE_EXPR is on the pending
sizes list, put newly created SAVE_EXPR there as well.
* gcc.c-torture/execute/20010209-1.c: New test.
* config/ia64/ia64.c (last_group): Only 2 entries are needed.
(errata_find_address_regs): load_group has only 2 entries.
(errata_emit_nops): Likewise. shladd is not problematic.
Clear last_group if nop was emitted.
(fixup_errata): load_group has only 2 entries.
Optimize.
git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/trunk@39663 138bc75d-0d04-0410-961f-82ee72b054a4
-rw-r--r-- | gcc/ChangeLog | 39 | ||||
-rw-r--r-- | gcc/config/ia64/ia64.c | 22 | ||||
-rw-r--r-- | gcc/fold-const.c | 9 | ||||
-rw-r--r-- | gcc/stor-layout.c | 28 | ||||
-rw-r--r-- | gcc/testsuite/ChangeLog | 4 | ||||
-rw-r--r-- | gcc/testsuite/gcc.c-torture/execute/20010209-1.c | 21 | ||||
-rw-r--r-- | gcc/tree.h | 2 |
7 files changed, 105 insertions, 20 deletions
diff --git a/gcc/ChangeLog b/gcc/ChangeLog index 2566f278404..bde3b9e5ff4 100644 --- a/gcc/ChangeLog +++ b/gcc/ChangeLog @@ -1,16 +1,33 @@ +2001-02-14 Jakub Jelinek <jakub@redhat.com> + + * stor-layout.c (is_pending_size, put_pending_size): New functions. + (variable_size): Call put_pending_size. + * tree.h (is_pending_size, put_pending_size): Add prototypes. + * fold-const.c (extract_muldiv): If SAVE_EXPR is on the pending + sizes list, put newly created SAVE_EXPR there as well. + +2001-02-14 Jakub Jelinek <jakub@redhat.com> + + * config/ia64/ia64.c (last_group): Only 2 entries are needed. + (errata_find_address_regs): load_group has only 2 entries. + (errata_emit_nops): Likewise. shladd is not problematic. + Clear last_group if nop was emitted. + (fixup_errata): load_group has only 2 entries. + Optimize. + 2001-02-14 Neil Booth <neil@daikokuya.demon.co.uk> - * c-lex.c (lex_number): Only warn traditionally for U suffix - outside system macros. - * cppexp.c (parse_number): Similarly. - * cpplib.h (NODE_SYSHDR, cpp_sys_objmacro_p): New. - * cppmacro.c (struct cpp_macro): New member node. - (parse_args): Only warn about missing rest args if not - a system macro. - (funlike_invocation_p): Similarly for uninvoked funlike macros. - (cpp_sys_objmacro_p): New. - (_cpp_create_definition): Store the node with the macro defn. - Remember if the macro is defined in a system header. + * c-lex.c (lex_number): Only warn traditionally for U suffix + outside system macros. + * cppexp.c (parse_number): Similarly. + * cpplib.h (NODE_SYSHDR, cpp_sys_objmacro_p): New. + * cppmacro.c (struct cpp_macro): New member node. + (parse_args): Only warn about missing rest args if not + a system macro. + (funlike_invocation_p): Similarly for uninvoked funlike macros. + (cpp_sys_objmacro_p): New. + (_cpp_create_definition): Store the node with the macro defn. + Remember if the macro is defined in a system header. 2001-02-13 DJ Delorie <dj@redhat.com> diff --git a/gcc/config/ia64/ia64.c b/gcc/config/ia64/ia64.c index 2eaafc7ca06..8b9e0b01457 100644 --- a/gcc/config/ia64/ia64.c +++ b/gcc/config/ia64/ia64.c @@ -4560,7 +4560,7 @@ static struct group { HARD_REG_SET p_reg_set; HARD_REG_SET gr_reg_conditionally_set; -} last_group[3]; +} last_group[2]; /* Index into the last_group array. */ static int group_idx; @@ -4581,7 +4581,7 @@ errata_find_address_regs (xp, data) x = XEXP (x, 0); if (GET_CODE (x) == REG) { - struct group *prev_group = last_group + (group_idx + 2) % 3; + struct group *prev_group = last_group + (group_idx ^ 1); if (TEST_HARD_REG_BIT (prev_group->gr_reg_conditionally_set, REGNO (x))) return 1; @@ -4598,7 +4598,7 @@ errata_emit_nops (insn) rtx insn; { struct group *this_group = last_group + group_idx; - struct group *prev_group = last_group + (group_idx + 2) % 3; + struct group *prev_group = last_group + (group_idx ^ 1); rtx pat = PATTERN (insn); rtx cond = GET_CODE (pat) == COND_EXEC ? COND_EXEC_TEST (pat) : 0; rtx real_pat = cond ? COND_EXEC_CODE (pat) : pat; @@ -4642,6 +4642,8 @@ errata_emit_nops (insn) && REG_P (SET_DEST (set)) && GET_CODE (SET_SRC (set)) != PLUS && GET_CODE (SET_SRC (set)) != MINUS + && (GET_CODE (SET_SRC (set)) != ASHIFT + || !shladd_operand (XEXP (SET_SRC (set), 1))) && (GET_CODE (SET_SRC (set)) != MEM || GET_CODE (XEXP (SET_SRC (set), 0)) != POST_MODIFY) && GENERAL_REGNO_P (REGNO (SET_DEST (set)))) @@ -4658,6 +4660,8 @@ errata_emit_nops (insn) emit_insn_before (gen_insn_group_barrier (GEN_INT (3)), insn); emit_insn_before (gen_nop (), insn); emit_insn_before (gen_insn_group_barrier (GEN_INT (3)), insn); + group_idx = 0; + memset (last_group, 0, sizeof last_group); } } @@ -4668,17 +4672,23 @@ fixup_errata () { rtx insn; + if (! TARGET_B_STEP) + return; + group_idx = 0; memset (last_group, 0, sizeof last_group); for (insn = get_insns (); insn; insn = NEXT_INSN (insn)) { - if (INSN_P (insn) && ia64_safe_type (insn) == TYPE_S) + if (!INSN_P (insn)) + continue; + + if (ia64_safe_type (insn) == TYPE_S) { - group_idx = (group_idx + 1) % 3; + group_idx ^= 1; memset (last_group + group_idx, 0, sizeof last_group[group_idx]); } - if (TARGET_B_STEP && INSN_P (insn)) + else errata_emit_nops (insn); } } diff --git a/gcc/fold-const.c b/gcc/fold-const.c index 3cb1869981b..3975ae414e4 100644 --- a/gcc/fold-const.c +++ b/gcc/fold-const.c @@ -4449,7 +4449,14 @@ extract_muldiv (t, c, code, wide_type) if (SAVE_EXPR_RTL (t) == 0 && ! TREE_SIDE_EFFECTS (TREE_OPERAND (t, 0)) && 0 != (t1 = extract_muldiv (TREE_OPERAND (t, 0), c, code, wide_type))) - return save_expr (t1); + { + t1 = save_expr (t1); + if (SAVE_EXPR_PERSISTENT_P (t) && TREE_CODE (t1) == SAVE_EXPR) + SAVE_EXPR_PERSISTENT_P (t1) = 1; + if (is_pending_size (t)) + put_pending_size (t1); + return t1; + } break; case LSHIFT_EXPR: case RSHIFT_EXPR: diff --git a/gcc/stor-layout.c b/gcc/stor-layout.c index 7bb5b4a2636..065d4f61201 100644 --- a/gcc/stor-layout.c +++ b/gcc/stor-layout.c @@ -94,6 +94,30 @@ get_pending_sizes () return chain; } +/* Return non-zero if EXPR is present on the pending sizes list. */ + +int +is_pending_size (expr) + tree expr; +{ + tree t; + + for (t = pending_sizes; t; t = TREE_CHAIN (t)) + if (TREE_VALUE (t) == expr) + return 1; + return 0; +} + +/* Add EXPR to the pending sizes list. */ + +void +put_pending_size (expr) + tree expr; +{ + if (TREE_CODE (expr) == SAVE_EXPR) + pending_sizes = tree_cons (NULL_TREE, expr, pending_sizes); +} + /* Put a chain of objects into the pending sizes list, which must be empty. */ @@ -153,8 +177,8 @@ variable_size (size) /* The front-end doesn't want us to keep a list of the expressions that determine sizes for variable size objects. */ ; - else if (TREE_CODE (size) == SAVE_EXPR) - pending_sizes = tree_cons (NULL_TREE, size, pending_sizes); + else + put_pending_size (size); return size; } diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog index d5b4ff1f8e5..8a5f0f03e83 100644 --- a/gcc/testsuite/ChangeLog +++ b/gcc/testsuite/ChangeLog @@ -1,3 +1,7 @@ +2001-02-14 Jakub Jelinek <jakub@redhat.com> + + * gcc.c-torture/execute/20010209-1.c: New test. + 2001-02-14 Neil Booth <neil@daikokuya.demon.co.uk> * gcc.dg/cpp/sysmac1.c, sysmac2.c: New tests. diff --git a/gcc/testsuite/gcc.c-torture/execute/20010209-1.c b/gcc/testsuite/gcc.c-torture/execute/20010209-1.c new file mode 100644 index 00000000000..e04d605ed63 --- /dev/null +++ b/gcc/testsuite/gcc.c-torture/execute/20010209-1.c @@ -0,0 +1,21 @@ +int b; +int foo (void) +{ + int x[b]; + int bar (int t[b]) + { + int i; + for (i = 0; i < b; i++) + t[i] = i + (i > 0 ? t[i-1] : 0); + return t[b-1]; + } + return bar (x); +} + +int main () +{ + b = 6; + if (foo () != 15) + abort (); + exit (0); +} diff --git a/gcc/tree.h b/gcc/tree.h index 33597d6f556..c7745be369b 100644 --- a/gcc/tree.h +++ b/gcc/tree.h @@ -2165,6 +2165,8 @@ extern tree size_int_type_wide PARAMS ((HOST_WIDE_INT, tree)); extern tree round_up PARAMS ((tree, int)); extern tree round_down PARAMS ((tree, int)); extern tree get_pending_sizes PARAMS ((void)); +extern int is_pending_size PARAMS ((tree)); +extern void put_pending_size PARAMS ((tree)); extern void put_pending_sizes PARAMS ((tree)); /* Type for sizes of data-type. */ |