From 53309b203442541ace0cbb0e8e7eed5dd3cbac50 Mon Sep 17 00:00:00 2001 From: davem Date: Sat, 12 Sep 1998 01:03:36 +0000 Subject: [PATCH] * flow.c (mark_set_1): Recognize multi-register structure return values in CALL insns. (mark_used_regs): Likewise. (count_reg_sets_1): Likewise. (count_reg_references): Likewise. * rtlanal.c (note_stores): Likewise. git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/trunk@22395 138bc75d-0d04-0410-961f-82ee72b054a4 --- gcc/ChangeLog | 9 +++++++++ gcc/flow.c | 38 ++++++++++++++++++++++++++++++++------ gcc/rtlanal.c | 21 +++++++++++++++++++-- 3 files changed, 60 insertions(+), 8 deletions(-) diff --git a/gcc/ChangeLog b/gcc/ChangeLog index 6b2f642deff..63646a0f67a 100644 --- a/gcc/ChangeLog +++ b/gcc/ChangeLog @@ -1,3 +1,12 @@ +Fri Sep 11 23:55:54 1998 David S. Miller + + * flow.c (mark_set_1): Recognize multi-register structure return + values in CALL insns. + (mark_used_regs): Likewise. + (count_reg_sets_1): Likewise. + (count_reg_references): Likewise. + * rtlanal.c (note_stores): Likewise. + Fri Sep 11 22:57:55 1998 Eric Dumazet * config/i386/sco5.h (ASM_WEAKEN_LABEL): Defined as in svr4.h. diff --git a/gcc/flow.c b/gcc/flow.c index af9eb1cde83..a7ce4a367e0 100644 --- a/gcc/flow.c +++ b/gcc/flow.c @@ -2133,6 +2133,19 @@ mark_set_1 (needed, dead, x, insn, significant) register int regno; register rtx reg = SET_DEST (x); + /* Some targets place small structures in registers for + return values of functions. We have to detect this + case specially here to get correct flow information. */ + if (GET_CODE (reg) == PARALLEL + && GET_MODE (reg) == BLKmode) + { + register int i; + + for (i = XVECLEN (reg, 0) - 1; i >= 0; i--) + mark_set_1 (needed, dead, XVECEXP (reg, 0, i), insn, significant); + return; + } + /* Modifying just one hardware register of a multi-reg value or just a byte field of a register does not mean the value from before this insn is now dead. @@ -2794,15 +2807,17 @@ mark_used_regs (needed, live, x, final, insn) /* If this is a store into a register, recursively scan the value being stored. */ - if (GET_CODE (testreg) == REG - && (regno = REGNO (testreg), regno != FRAME_POINTER_REGNUM) + if ((GET_CODE (testreg) == PARALLEL + && GET_MODE (testreg) == BLKmode) + || (GET_CODE (testreg) == REG + && (regno = REGNO (testreg), regno != FRAME_POINTER_REGNUM) #if FRAME_POINTER_REGNUM != HARD_FRAME_POINTER_REGNUM - && regno != HARD_FRAME_POINTER_REGNUM + && regno != HARD_FRAME_POINTER_REGNUM #endif #if FRAME_POINTER_REGNUM != ARG_POINTER_REGNUM - && ! (regno == ARG_POINTER_REGNUM && fixed_regs[regno]) + && ! (regno == ARG_POINTER_REGNUM && fixed_regs[regno]) #endif - ) + )) /* We used to exclude global_regs here, but that seems wrong. Storing in them is like storing in mem. */ { @@ -4043,6 +4058,15 @@ count_reg_sets_1 (x) || GET_CODE (reg) == STRICT_LOW_PART) reg = XEXP (reg, 0); + if (GET_CODE (reg) == PARALLEL + && GET_MODE (reg) == BLKmode) + { + register int i; + for (i = XVECLEN (reg, 0) - 1; i >= 0; i--) + count_reg_sets_1 (XVECEXP (reg, 0, i)); + return; + } + if (GET_CODE (reg) == REG) { regno = REGNO (reg); @@ -4175,7 +4199,9 @@ count_reg_references (x) /* If this is a store into a register, recursively scan the value being stored. */ - if (GET_CODE (testreg) == REG) + if ((GET_CODE (testreg) == PARALLEL + && GET_MODE (testreg) == BLKmode) + || GET_CODE (testreg) == REG) { count_reg_references (SET_SRC (x)); if (mark_dest) diff --git a/gcc/rtlanal.c b/gcc/rtlanal.c index fb4176264b3..41625ee2868 100644 --- a/gcc/rtlanal.c +++ b/gcc/rtlanal.c @@ -1086,7 +1086,16 @@ note_stores (x, fun) || GET_CODE (dest) == SIGN_EXTRACT || GET_CODE (dest) == STRICT_LOW_PART) dest = XEXP (dest, 0); - (*fun) (dest, x); + + if (GET_CODE (dest) == PARALLEL + && GET_MODE (dest) == BLKmode) + { + register int i; + for (i = XVECLEN (dest, 0) - 1; i >= 0; i--) + (*fun) (SET_DEST (XVECEXP (dest, 0, i)), x); + } + else + (*fun) (dest, x); } else if (GET_CODE (x) == PARALLEL) { @@ -1105,7 +1114,15 @@ note_stores (x, fun) || GET_CODE (dest) == SIGN_EXTRACT || GET_CODE (dest) == STRICT_LOW_PART) dest = XEXP (dest, 0); - (*fun) (dest, y); + if (GET_CODE (dest) == PARALLEL + && GET_MODE (dest) == BLKmode) + { + register int i; + for (i = XVECLEN (dest, 0) - 1; i >= 0; i--) + (*fun) (SET_DEST (XVECEXP (dest, 0, i)), y); + } + else + (*fun) (dest, y); } } } -- 2.11.4.GIT