1*e4b17023SJohn Marino /* Register to Stack convert for GNU compiler. 2*e4b17023SJohn Marino Copyright (C) 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999, 2000, 3*e4b17023SJohn Marino 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2010, 2011, 2012 4*e4b17023SJohn Marino Free Software Foundation, Inc. 5*e4b17023SJohn Marino 6*e4b17023SJohn Marino This file is part of GCC. 7*e4b17023SJohn Marino 8*e4b17023SJohn Marino GCC is free software; you can redistribute it and/or modify it 9*e4b17023SJohn Marino under the terms of the GNU General Public License as published by 10*e4b17023SJohn Marino the Free Software Foundation; either version 3, or (at your option) 11*e4b17023SJohn Marino any later version. 12*e4b17023SJohn Marino 13*e4b17023SJohn Marino GCC is distributed in the hope that it will be useful, but WITHOUT 14*e4b17023SJohn Marino ANY WARRANTY; without even the implied warranty of MERCHANTABILITY 15*e4b17023SJohn Marino or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public 16*e4b17023SJohn Marino License for more details. 17*e4b17023SJohn Marino 18*e4b17023SJohn Marino You should have received a copy of the GNU General Public License 19*e4b17023SJohn Marino along with GCC; see the file COPYING3. If not see 20*e4b17023SJohn Marino <http://www.gnu.org/licenses/>. */ 21*e4b17023SJohn Marino 22*e4b17023SJohn Marino /* This pass converts stack-like registers from the "flat register 23*e4b17023SJohn Marino file" model that gcc uses, to a stack convention that the 387 uses. 24*e4b17023SJohn Marino 25*e4b17023SJohn Marino * The form of the input: 26*e4b17023SJohn Marino 27*e4b17023SJohn Marino On input, the function consists of insn that have had their 28*e4b17023SJohn Marino registers fully allocated to a set of "virtual" registers. Note that 29*e4b17023SJohn Marino the word "virtual" is used differently here than elsewhere in gcc: for 30*e4b17023SJohn Marino each virtual stack reg, there is a hard reg, but the mapping between 31*e4b17023SJohn Marino them is not known until this pass is run. On output, hard register 32*e4b17023SJohn Marino numbers have been substituted, and various pop and exchange insns have 33*e4b17023SJohn Marino been emitted. The hard register numbers and the virtual register 34*e4b17023SJohn Marino numbers completely overlap - before this pass, all stack register 35*e4b17023SJohn Marino numbers are virtual, and afterward they are all hard. 36*e4b17023SJohn Marino 37*e4b17023SJohn Marino The virtual registers can be manipulated normally by gcc, and their 38*e4b17023SJohn Marino semantics are the same as for normal registers. After the hard 39*e4b17023SJohn Marino register numbers are substituted, the semantics of an insn containing 40*e4b17023SJohn Marino stack-like regs are not the same as for an insn with normal regs: for 41*e4b17023SJohn Marino instance, it is not safe to delete an insn that appears to be a no-op 42*e4b17023SJohn Marino move. In general, no insn containing hard regs should be changed 43*e4b17023SJohn Marino after this pass is done. 44*e4b17023SJohn Marino 45*e4b17023SJohn Marino * The form of the output: 46*e4b17023SJohn Marino 47*e4b17023SJohn Marino After this pass, hard register numbers represent the distance from 48*e4b17023SJohn Marino the current top of stack to the desired register. A reference to 49*e4b17023SJohn Marino FIRST_STACK_REG references the top of stack, FIRST_STACK_REG + 1, 50*e4b17023SJohn Marino represents the register just below that, and so forth. Also, REG_DEAD 51*e4b17023SJohn Marino notes indicate whether or not a stack register should be popped. 52*e4b17023SJohn Marino 53*e4b17023SJohn Marino A "swap" insn looks like a parallel of two patterns, where each 54*e4b17023SJohn Marino pattern is a SET: one sets A to B, the other B to A. 55*e4b17023SJohn Marino 56*e4b17023SJohn Marino A "push" or "load" insn is a SET whose SET_DEST is FIRST_STACK_REG 57*e4b17023SJohn Marino and whose SET_DEST is REG or MEM. Any other SET_DEST, such as PLUS, 58*e4b17023SJohn Marino will replace the existing stack top, not push a new value. 59*e4b17023SJohn Marino 60*e4b17023SJohn Marino A store insn is a SET whose SET_DEST is FIRST_STACK_REG, and whose 61*e4b17023SJohn Marino SET_SRC is REG or MEM. 62*e4b17023SJohn Marino 63*e4b17023SJohn Marino The case where the SET_SRC and SET_DEST are both FIRST_STACK_REG 64*e4b17023SJohn Marino appears ambiguous. As a special case, the presence of a REG_DEAD note 65*e4b17023SJohn Marino for FIRST_STACK_REG differentiates between a load insn and a pop. 66*e4b17023SJohn Marino 67*e4b17023SJohn Marino If a REG_DEAD is present, the insn represents a "pop" that discards 68*e4b17023SJohn Marino the top of the register stack. If there is no REG_DEAD note, then the 69*e4b17023SJohn Marino insn represents a "dup" or a push of the current top of stack onto the 70*e4b17023SJohn Marino stack. 71*e4b17023SJohn Marino 72*e4b17023SJohn Marino * Methodology: 73*e4b17023SJohn Marino 74*e4b17023SJohn Marino Existing REG_DEAD and REG_UNUSED notes for stack registers are 75*e4b17023SJohn Marino deleted and recreated from scratch. REG_DEAD is never created for a 76*e4b17023SJohn Marino SET_DEST, only REG_UNUSED. 77*e4b17023SJohn Marino 78*e4b17023SJohn Marino * asm_operands: 79*e4b17023SJohn Marino 80*e4b17023SJohn Marino There are several rules on the usage of stack-like regs in 81*e4b17023SJohn Marino asm_operands insns. These rules apply only to the operands that are 82*e4b17023SJohn Marino stack-like regs: 83*e4b17023SJohn Marino 84*e4b17023SJohn Marino 1. Given a set of input regs that die in an asm_operands, it is 85*e4b17023SJohn Marino necessary to know which are implicitly popped by the asm, and 86*e4b17023SJohn Marino which must be explicitly popped by gcc. 87*e4b17023SJohn Marino 88*e4b17023SJohn Marino An input reg that is implicitly popped by the asm must be 89*e4b17023SJohn Marino explicitly clobbered, unless it is constrained to match an 90*e4b17023SJohn Marino output operand. 91*e4b17023SJohn Marino 92*e4b17023SJohn Marino 2. For any input reg that is implicitly popped by an asm, it is 93*e4b17023SJohn Marino necessary to know how to adjust the stack to compensate for the pop. 94*e4b17023SJohn Marino If any non-popped input is closer to the top of the reg-stack than 95*e4b17023SJohn Marino the implicitly popped reg, it would not be possible to know what the 96*e4b17023SJohn Marino stack looked like - it's not clear how the rest of the stack "slides 97*e4b17023SJohn Marino up". 98*e4b17023SJohn Marino 99*e4b17023SJohn Marino All implicitly popped input regs must be closer to the top of 100*e4b17023SJohn Marino the reg-stack than any input that is not implicitly popped. 101*e4b17023SJohn Marino 102*e4b17023SJohn Marino 3. It is possible that if an input dies in an insn, reload might 103*e4b17023SJohn Marino use the input reg for an output reload. Consider this example: 104*e4b17023SJohn Marino 105*e4b17023SJohn Marino asm ("foo" : "=t" (a) : "f" (b)); 106*e4b17023SJohn Marino 107*e4b17023SJohn Marino This asm says that input B is not popped by the asm, and that 108*e4b17023SJohn Marino the asm pushes a result onto the reg-stack, i.e., the stack is one 109*e4b17023SJohn Marino deeper after the asm than it was before. But, it is possible that 110*e4b17023SJohn Marino reload will think that it can use the same reg for both the input and 111*e4b17023SJohn Marino the output, if input B dies in this insn. 112*e4b17023SJohn Marino 113*e4b17023SJohn Marino If any input operand uses the "f" constraint, all output reg 114*e4b17023SJohn Marino constraints must use the "&" earlyclobber. 115*e4b17023SJohn Marino 116*e4b17023SJohn Marino The asm above would be written as 117*e4b17023SJohn Marino 118*e4b17023SJohn Marino asm ("foo" : "=&t" (a) : "f" (b)); 119*e4b17023SJohn Marino 120*e4b17023SJohn Marino 4. Some operands need to be in particular places on the stack. All 121*e4b17023SJohn Marino output operands fall in this category - there is no other way to 122*e4b17023SJohn Marino know which regs the outputs appear in unless the user indicates 123*e4b17023SJohn Marino this in the constraints. 124*e4b17023SJohn Marino 125*e4b17023SJohn Marino Output operands must specifically indicate which reg an output 126*e4b17023SJohn Marino appears in after an asm. "=f" is not allowed: the operand 127*e4b17023SJohn Marino constraints must select a class with a single reg. 128*e4b17023SJohn Marino 129*e4b17023SJohn Marino 5. Output operands may not be "inserted" between existing stack regs. 130*e4b17023SJohn Marino Since no 387 opcode uses a read/write operand, all output operands 131*e4b17023SJohn Marino are dead before the asm_operands, and are pushed by the asm_operands. 132*e4b17023SJohn Marino It makes no sense to push anywhere but the top of the reg-stack. 133*e4b17023SJohn Marino 134*e4b17023SJohn Marino Output operands must start at the top of the reg-stack: output 135*e4b17023SJohn Marino operands may not "skip" a reg. 136*e4b17023SJohn Marino 137*e4b17023SJohn Marino 6. Some asm statements may need extra stack space for internal 138*e4b17023SJohn Marino calculations. This can be guaranteed by clobbering stack registers 139*e4b17023SJohn Marino unrelated to the inputs and outputs. 140*e4b17023SJohn Marino 141*e4b17023SJohn Marino Here are a couple of reasonable asms to want to write. This asm 142*e4b17023SJohn Marino takes one input, which is internally popped, and produces two outputs. 143*e4b17023SJohn Marino 144*e4b17023SJohn Marino asm ("fsincos" : "=t" (cos), "=u" (sin) : "0" (inp)); 145*e4b17023SJohn Marino 146*e4b17023SJohn Marino This asm takes two inputs, which are popped by the fyl2xp1 opcode, 147*e4b17023SJohn Marino and replaces them with one output. The user must code the "st(1)" 148*e4b17023SJohn Marino clobber for reg-stack.c to know that fyl2xp1 pops both inputs. 149*e4b17023SJohn Marino 150*e4b17023SJohn Marino asm ("fyl2xp1" : "=t" (result) : "0" (x), "u" (y) : "st(1)"); 151*e4b17023SJohn Marino 152*e4b17023SJohn Marino */ 153*e4b17023SJohn Marino 154*e4b17023SJohn Marino #include "config.h" 155*e4b17023SJohn Marino #include "system.h" 156*e4b17023SJohn Marino #include "coretypes.h" 157*e4b17023SJohn Marino #include "tm.h" 158*e4b17023SJohn Marino #include "tree.h" 159*e4b17023SJohn Marino #include "rtl-error.h" 160*e4b17023SJohn Marino #include "tm_p.h" 161*e4b17023SJohn Marino #include "function.h" 162*e4b17023SJohn Marino #include "insn-config.h" 163*e4b17023SJohn Marino #include "regs.h" 164*e4b17023SJohn Marino #include "hard-reg-set.h" 165*e4b17023SJohn Marino #include "flags.h" 166*e4b17023SJohn Marino #include "recog.h" 167*e4b17023SJohn Marino #include "output.h" 168*e4b17023SJohn Marino #include "basic-block.h" 169*e4b17023SJohn Marino #include "cfglayout.h" 170*e4b17023SJohn Marino #include "reload.h" 171*e4b17023SJohn Marino #include "ggc.h" 172*e4b17023SJohn Marino #include "timevar.h" 173*e4b17023SJohn Marino #include "tree-pass.h" 174*e4b17023SJohn Marino #include "target.h" 175*e4b17023SJohn Marino #include "df.h" 176*e4b17023SJohn Marino #include "vecprim.h" 177*e4b17023SJohn Marino #include "emit-rtl.h" /* FIXME: Can go away once crtl is moved to rtl.h. */ 178*e4b17023SJohn Marino 179*e4b17023SJohn Marino #ifdef STACK_REGS 180*e4b17023SJohn Marino 181*e4b17023SJohn Marino /* We use this array to cache info about insns, because otherwise we 182*e4b17023SJohn Marino spend too much time in stack_regs_mentioned_p. 183*e4b17023SJohn Marino 184*e4b17023SJohn Marino Indexed by insn UIDs. A value of zero is uninitialized, one indicates 185*e4b17023SJohn Marino the insn uses stack registers, two indicates the insn does not use 186*e4b17023SJohn Marino stack registers. */ 187*e4b17023SJohn Marino static VEC(char,heap) *stack_regs_mentioned_data; 188*e4b17023SJohn Marino 189*e4b17023SJohn Marino #define REG_STACK_SIZE (LAST_STACK_REG - FIRST_STACK_REG + 1) 190*e4b17023SJohn Marino 191*e4b17023SJohn Marino int regstack_completed = 0; 192*e4b17023SJohn Marino 193*e4b17023SJohn Marino /* This is the basic stack record. TOP is an index into REG[] such 194*e4b17023SJohn Marino that REG[TOP] is the top of stack. If TOP is -1 the stack is empty. 195*e4b17023SJohn Marino 196*e4b17023SJohn Marino If TOP is -2, REG[] is not yet initialized. Stack initialization 197*e4b17023SJohn Marino consists of placing each live reg in array `reg' and setting `top' 198*e4b17023SJohn Marino appropriately. 199*e4b17023SJohn Marino 200*e4b17023SJohn Marino REG_SET indicates which registers are live. */ 201*e4b17023SJohn Marino 202*e4b17023SJohn Marino typedef struct stack_def 203*e4b17023SJohn Marino { 204*e4b17023SJohn Marino int top; /* index to top stack element */ 205*e4b17023SJohn Marino HARD_REG_SET reg_set; /* set of live registers */ 206*e4b17023SJohn Marino unsigned char reg[REG_STACK_SIZE];/* register - stack mapping */ 207*e4b17023SJohn Marino } *stack; 208*e4b17023SJohn Marino 209*e4b17023SJohn Marino /* This is used to carry information about basic blocks. It is 210*e4b17023SJohn Marino attached to the AUX field of the standard CFG block. */ 211*e4b17023SJohn Marino 212*e4b17023SJohn Marino typedef struct block_info_def 213*e4b17023SJohn Marino { 214*e4b17023SJohn Marino struct stack_def stack_in; /* Input stack configuration. */ 215*e4b17023SJohn Marino struct stack_def stack_out; /* Output stack configuration. */ 216*e4b17023SJohn Marino HARD_REG_SET out_reg_set; /* Stack regs live on output. */ 217*e4b17023SJohn Marino int done; /* True if block already converted. */ 218*e4b17023SJohn Marino int predecessors; /* Number of predecessors that need 219*e4b17023SJohn Marino to be visited. */ 220*e4b17023SJohn Marino } *block_info; 221*e4b17023SJohn Marino 222*e4b17023SJohn Marino #define BLOCK_INFO(B) ((block_info) (B)->aux) 223*e4b17023SJohn Marino 224*e4b17023SJohn Marino /* Passed to change_stack to indicate where to emit insns. */ 225*e4b17023SJohn Marino enum emit_where 226*e4b17023SJohn Marino { 227*e4b17023SJohn Marino EMIT_AFTER, 228*e4b17023SJohn Marino EMIT_BEFORE 229*e4b17023SJohn Marino }; 230*e4b17023SJohn Marino 231*e4b17023SJohn Marino /* The block we're currently working on. */ 232*e4b17023SJohn Marino static basic_block current_block; 233*e4b17023SJohn Marino 234*e4b17023SJohn Marino /* In the current_block, whether we're processing the first register 235*e4b17023SJohn Marino stack or call instruction, i.e. the regstack is currently the 236*e4b17023SJohn Marino same as BLOCK_INFO(current_block)->stack_in. */ 237*e4b17023SJohn Marino static bool starting_stack_p; 238*e4b17023SJohn Marino 239*e4b17023SJohn Marino /* This is the register file for all register after conversion. */ 240*e4b17023SJohn Marino static rtx 241*e4b17023SJohn Marino FP_mode_reg[LAST_STACK_REG+1-FIRST_STACK_REG][(int) MAX_MACHINE_MODE]; 242*e4b17023SJohn Marino 243*e4b17023SJohn Marino #define FP_MODE_REG(regno,mode) \ 244*e4b17023SJohn Marino (FP_mode_reg[(regno)-FIRST_STACK_REG][(int) (mode)]) 245*e4b17023SJohn Marino 246*e4b17023SJohn Marino /* Used to initialize uninitialized registers. */ 247*e4b17023SJohn Marino static rtx not_a_num; 248*e4b17023SJohn Marino 249*e4b17023SJohn Marino /* Forward declarations */ 250*e4b17023SJohn Marino 251*e4b17023SJohn Marino static int stack_regs_mentioned_p (const_rtx pat); 252*e4b17023SJohn Marino static void pop_stack (stack, int); 253*e4b17023SJohn Marino static rtx *get_true_reg (rtx *); 254*e4b17023SJohn Marino 255*e4b17023SJohn Marino static int check_asm_stack_operands (rtx); 256*e4b17023SJohn Marino static void get_asm_operands_in_out (rtx, int *, int *); 257*e4b17023SJohn Marino static rtx stack_result (tree); 258*e4b17023SJohn Marino static void replace_reg (rtx *, int); 259*e4b17023SJohn Marino static void remove_regno_note (rtx, enum reg_note, unsigned int); 260*e4b17023SJohn Marino static int get_hard_regnum (stack, rtx); 261*e4b17023SJohn Marino static rtx emit_pop_insn (rtx, stack, rtx, enum emit_where); 262*e4b17023SJohn Marino static void swap_to_top(rtx, stack, rtx, rtx); 263*e4b17023SJohn Marino static bool move_for_stack_reg (rtx, stack, rtx); 264*e4b17023SJohn Marino static bool move_nan_for_stack_reg (rtx, stack, rtx); 265*e4b17023SJohn Marino static int swap_rtx_condition_1 (rtx); 266*e4b17023SJohn Marino static int swap_rtx_condition (rtx); 267*e4b17023SJohn Marino static void compare_for_stack_reg (rtx, stack, rtx); 268*e4b17023SJohn Marino static bool subst_stack_regs_pat (rtx, stack, rtx); 269*e4b17023SJohn Marino static void subst_asm_stack_regs (rtx, stack); 270*e4b17023SJohn Marino static bool subst_stack_regs (rtx, stack); 271*e4b17023SJohn Marino static void change_stack (rtx, stack, stack, enum emit_where); 272*e4b17023SJohn Marino static void print_stack (FILE *, stack); 273*e4b17023SJohn Marino static rtx next_flags_user (rtx); 274*e4b17023SJohn Marino 275*e4b17023SJohn Marino /* Return nonzero if any stack register is mentioned somewhere within PAT. */ 276*e4b17023SJohn Marino 277*e4b17023SJohn Marino static int 278*e4b17023SJohn Marino stack_regs_mentioned_p (const_rtx pat) 279*e4b17023SJohn Marino { 280*e4b17023SJohn Marino const char *fmt; 281*e4b17023SJohn Marino int i; 282*e4b17023SJohn Marino 283*e4b17023SJohn Marino if (STACK_REG_P (pat)) 284*e4b17023SJohn Marino return 1; 285*e4b17023SJohn Marino 286*e4b17023SJohn Marino fmt = GET_RTX_FORMAT (GET_CODE (pat)); 287*e4b17023SJohn Marino for (i = GET_RTX_LENGTH (GET_CODE (pat)) - 1; i >= 0; i--) 288*e4b17023SJohn Marino { 289*e4b17023SJohn Marino if (fmt[i] == 'E') 290*e4b17023SJohn Marino { 291*e4b17023SJohn Marino int j; 292*e4b17023SJohn Marino 293*e4b17023SJohn Marino for (j = XVECLEN (pat, i) - 1; j >= 0; j--) 294*e4b17023SJohn Marino if (stack_regs_mentioned_p (XVECEXP (pat, i, j))) 295*e4b17023SJohn Marino return 1; 296*e4b17023SJohn Marino } 297*e4b17023SJohn Marino else if (fmt[i] == 'e' && stack_regs_mentioned_p (XEXP (pat, i))) 298*e4b17023SJohn Marino return 1; 299*e4b17023SJohn Marino } 300*e4b17023SJohn Marino 301*e4b17023SJohn Marino return 0; 302*e4b17023SJohn Marino } 303*e4b17023SJohn Marino 304*e4b17023SJohn Marino /* Return nonzero if INSN mentions stacked registers, else return zero. */ 305*e4b17023SJohn Marino 306*e4b17023SJohn Marino int 307*e4b17023SJohn Marino stack_regs_mentioned (const_rtx insn) 308*e4b17023SJohn Marino { 309*e4b17023SJohn Marino unsigned int uid, max; 310*e4b17023SJohn Marino int test; 311*e4b17023SJohn Marino 312*e4b17023SJohn Marino if (! INSN_P (insn) || !stack_regs_mentioned_data) 313*e4b17023SJohn Marino return 0; 314*e4b17023SJohn Marino 315*e4b17023SJohn Marino uid = INSN_UID (insn); 316*e4b17023SJohn Marino max = VEC_length (char, stack_regs_mentioned_data); 317*e4b17023SJohn Marino if (uid >= max) 318*e4b17023SJohn Marino { 319*e4b17023SJohn Marino /* Allocate some extra size to avoid too many reallocs, but 320*e4b17023SJohn Marino do not grow too quickly. */ 321*e4b17023SJohn Marino max = uid + uid / 20 + 1; 322*e4b17023SJohn Marino VEC_safe_grow_cleared (char, heap, stack_regs_mentioned_data, max); 323*e4b17023SJohn Marino } 324*e4b17023SJohn Marino 325*e4b17023SJohn Marino test = VEC_index (char, stack_regs_mentioned_data, uid); 326*e4b17023SJohn Marino if (test == 0) 327*e4b17023SJohn Marino { 328*e4b17023SJohn Marino /* This insn has yet to be examined. Do so now. */ 329*e4b17023SJohn Marino test = stack_regs_mentioned_p (PATTERN (insn)) ? 1 : 2; 330*e4b17023SJohn Marino VEC_replace (char, stack_regs_mentioned_data, uid, test); 331*e4b17023SJohn Marino } 332*e4b17023SJohn Marino 333*e4b17023SJohn Marino return test == 1; 334*e4b17023SJohn Marino } 335*e4b17023SJohn Marino 336*e4b17023SJohn Marino static rtx ix86_flags_rtx; 337*e4b17023SJohn Marino 338*e4b17023SJohn Marino static rtx 339*e4b17023SJohn Marino next_flags_user (rtx insn) 340*e4b17023SJohn Marino { 341*e4b17023SJohn Marino /* Search forward looking for the first use of this value. 342*e4b17023SJohn Marino Stop at block boundaries. */ 343*e4b17023SJohn Marino 344*e4b17023SJohn Marino while (insn != BB_END (current_block)) 345*e4b17023SJohn Marino { 346*e4b17023SJohn Marino insn = NEXT_INSN (insn); 347*e4b17023SJohn Marino 348*e4b17023SJohn Marino if (INSN_P (insn) && reg_mentioned_p (ix86_flags_rtx, PATTERN (insn))) 349*e4b17023SJohn Marino return insn; 350*e4b17023SJohn Marino 351*e4b17023SJohn Marino if (CALL_P (insn)) 352*e4b17023SJohn Marino return NULL_RTX; 353*e4b17023SJohn Marino } 354*e4b17023SJohn Marino return NULL_RTX; 355*e4b17023SJohn Marino } 356*e4b17023SJohn Marino 357*e4b17023SJohn Marino /* Reorganize the stack into ascending numbers, before this insn. */ 358*e4b17023SJohn Marino 359*e4b17023SJohn Marino static void 360*e4b17023SJohn Marino straighten_stack (rtx insn, stack regstack) 361*e4b17023SJohn Marino { 362*e4b17023SJohn Marino struct stack_def temp_stack; 363*e4b17023SJohn Marino int top; 364*e4b17023SJohn Marino 365*e4b17023SJohn Marino /* If there is only a single register on the stack, then the stack is 366*e4b17023SJohn Marino already in increasing order and no reorganization is needed. 367*e4b17023SJohn Marino 368*e4b17023SJohn Marino Similarly if the stack is empty. */ 369*e4b17023SJohn Marino if (regstack->top <= 0) 370*e4b17023SJohn Marino return; 371*e4b17023SJohn Marino 372*e4b17023SJohn Marino COPY_HARD_REG_SET (temp_stack.reg_set, regstack->reg_set); 373*e4b17023SJohn Marino 374*e4b17023SJohn Marino for (top = temp_stack.top = regstack->top; top >= 0; top--) 375*e4b17023SJohn Marino temp_stack.reg[top] = FIRST_STACK_REG + temp_stack.top - top; 376*e4b17023SJohn Marino 377*e4b17023SJohn Marino change_stack (insn, regstack, &temp_stack, EMIT_BEFORE); 378*e4b17023SJohn Marino } 379*e4b17023SJohn Marino 380*e4b17023SJohn Marino /* Pop a register from the stack. */ 381*e4b17023SJohn Marino 382*e4b17023SJohn Marino static void 383*e4b17023SJohn Marino pop_stack (stack regstack, int regno) 384*e4b17023SJohn Marino { 385*e4b17023SJohn Marino int top = regstack->top; 386*e4b17023SJohn Marino 387*e4b17023SJohn Marino CLEAR_HARD_REG_BIT (regstack->reg_set, regno); 388*e4b17023SJohn Marino regstack->top--; 389*e4b17023SJohn Marino /* If regno was not at the top of stack then adjust stack. */ 390*e4b17023SJohn Marino if (regstack->reg [top] != regno) 391*e4b17023SJohn Marino { 392*e4b17023SJohn Marino int i; 393*e4b17023SJohn Marino for (i = regstack->top; i >= 0; i--) 394*e4b17023SJohn Marino if (regstack->reg [i] == regno) 395*e4b17023SJohn Marino { 396*e4b17023SJohn Marino int j; 397*e4b17023SJohn Marino for (j = i; j < top; j++) 398*e4b17023SJohn Marino regstack->reg [j] = regstack->reg [j + 1]; 399*e4b17023SJohn Marino break; 400*e4b17023SJohn Marino } 401*e4b17023SJohn Marino } 402*e4b17023SJohn Marino } 403*e4b17023SJohn Marino 404*e4b17023SJohn Marino /* Return a pointer to the REG expression within PAT. If PAT is not a 405*e4b17023SJohn Marino REG, possible enclosed by a conversion rtx, return the inner part of 406*e4b17023SJohn Marino PAT that stopped the search. */ 407*e4b17023SJohn Marino 408*e4b17023SJohn Marino static rtx * 409*e4b17023SJohn Marino get_true_reg (rtx *pat) 410*e4b17023SJohn Marino { 411*e4b17023SJohn Marino for (;;) 412*e4b17023SJohn Marino switch (GET_CODE (*pat)) 413*e4b17023SJohn Marino { 414*e4b17023SJohn Marino case SUBREG: 415*e4b17023SJohn Marino /* Eliminate FP subregister accesses in favor of the 416*e4b17023SJohn Marino actual FP register in use. */ 417*e4b17023SJohn Marino { 418*e4b17023SJohn Marino rtx subreg; 419*e4b17023SJohn Marino if (FP_REG_P (subreg = SUBREG_REG (*pat))) 420*e4b17023SJohn Marino { 421*e4b17023SJohn Marino int regno_off = subreg_regno_offset (REGNO (subreg), 422*e4b17023SJohn Marino GET_MODE (subreg), 423*e4b17023SJohn Marino SUBREG_BYTE (*pat), 424*e4b17023SJohn Marino GET_MODE (*pat)); 425*e4b17023SJohn Marino *pat = FP_MODE_REG (REGNO (subreg) + regno_off, 426*e4b17023SJohn Marino GET_MODE (subreg)); 427*e4b17023SJohn Marino return pat; 428*e4b17023SJohn Marino } 429*e4b17023SJohn Marino } 430*e4b17023SJohn Marino case FLOAT: 431*e4b17023SJohn Marino case FIX: 432*e4b17023SJohn Marino case FLOAT_EXTEND: 433*e4b17023SJohn Marino pat = & XEXP (*pat, 0); 434*e4b17023SJohn Marino break; 435*e4b17023SJohn Marino 436*e4b17023SJohn Marino case UNSPEC: 437*e4b17023SJohn Marino if (XINT (*pat, 1) == UNSPEC_TRUNC_NOOP 438*e4b17023SJohn Marino || XINT (*pat, 1) == UNSPEC_LDA) 439*e4b17023SJohn Marino pat = & XVECEXP (*pat, 0, 0); 440*e4b17023SJohn Marino return pat; 441*e4b17023SJohn Marino 442*e4b17023SJohn Marino case FLOAT_TRUNCATE: 443*e4b17023SJohn Marino if (!flag_unsafe_math_optimizations) 444*e4b17023SJohn Marino return pat; 445*e4b17023SJohn Marino pat = & XEXP (*pat, 0); 446*e4b17023SJohn Marino break; 447*e4b17023SJohn Marino 448*e4b17023SJohn Marino default: 449*e4b17023SJohn Marino return pat; 450*e4b17023SJohn Marino } 451*e4b17023SJohn Marino } 452*e4b17023SJohn Marino 453*e4b17023SJohn Marino /* Set if we find any malformed asms in a block. */ 454*e4b17023SJohn Marino static bool any_malformed_asm; 455*e4b17023SJohn Marino 456*e4b17023SJohn Marino /* There are many rules that an asm statement for stack-like regs must 457*e4b17023SJohn Marino follow. Those rules are explained at the top of this file: the rule 458*e4b17023SJohn Marino numbers below refer to that explanation. */ 459*e4b17023SJohn Marino 460*e4b17023SJohn Marino static int 461*e4b17023SJohn Marino check_asm_stack_operands (rtx insn) 462*e4b17023SJohn Marino { 463*e4b17023SJohn Marino int i; 464*e4b17023SJohn Marino int n_clobbers; 465*e4b17023SJohn Marino int malformed_asm = 0; 466*e4b17023SJohn Marino rtx body = PATTERN (insn); 467*e4b17023SJohn Marino 468*e4b17023SJohn Marino char reg_used_as_output[FIRST_PSEUDO_REGISTER]; 469*e4b17023SJohn Marino char implicitly_dies[FIRST_PSEUDO_REGISTER]; 470*e4b17023SJohn Marino int alt; 471*e4b17023SJohn Marino 472*e4b17023SJohn Marino rtx *clobber_reg = 0; 473*e4b17023SJohn Marino int n_inputs, n_outputs; 474*e4b17023SJohn Marino 475*e4b17023SJohn Marino /* Find out what the constraints require. If no constraint 476*e4b17023SJohn Marino alternative matches, this asm is malformed. */ 477*e4b17023SJohn Marino extract_insn (insn); 478*e4b17023SJohn Marino constrain_operands (1); 479*e4b17023SJohn Marino alt = which_alternative; 480*e4b17023SJohn Marino 481*e4b17023SJohn Marino preprocess_constraints (); 482*e4b17023SJohn Marino 483*e4b17023SJohn Marino get_asm_operands_in_out (body, &n_outputs, &n_inputs); 484*e4b17023SJohn Marino 485*e4b17023SJohn Marino if (alt < 0) 486*e4b17023SJohn Marino { 487*e4b17023SJohn Marino malformed_asm = 1; 488*e4b17023SJohn Marino /* Avoid further trouble with this insn. */ 489*e4b17023SJohn Marino PATTERN (insn) = gen_rtx_USE (VOIDmode, const0_rtx); 490*e4b17023SJohn Marino return 0; 491*e4b17023SJohn Marino } 492*e4b17023SJohn Marino 493*e4b17023SJohn Marino /* Strip SUBREGs here to make the following code simpler. */ 494*e4b17023SJohn Marino for (i = 0; i < recog_data.n_operands; i++) 495*e4b17023SJohn Marino if (GET_CODE (recog_data.operand[i]) == SUBREG 496*e4b17023SJohn Marino && REG_P (SUBREG_REG (recog_data.operand[i]))) 497*e4b17023SJohn Marino recog_data.operand[i] = SUBREG_REG (recog_data.operand[i]); 498*e4b17023SJohn Marino 499*e4b17023SJohn Marino /* Set up CLOBBER_REG. */ 500*e4b17023SJohn Marino 501*e4b17023SJohn Marino n_clobbers = 0; 502*e4b17023SJohn Marino 503*e4b17023SJohn Marino if (GET_CODE (body) == PARALLEL) 504*e4b17023SJohn Marino { 505*e4b17023SJohn Marino clobber_reg = XALLOCAVEC (rtx, XVECLEN (body, 0)); 506*e4b17023SJohn Marino 507*e4b17023SJohn Marino for (i = 0; i < XVECLEN (body, 0); i++) 508*e4b17023SJohn Marino if (GET_CODE (XVECEXP (body, 0, i)) == CLOBBER) 509*e4b17023SJohn Marino { 510*e4b17023SJohn Marino rtx clobber = XVECEXP (body, 0, i); 511*e4b17023SJohn Marino rtx reg = XEXP (clobber, 0); 512*e4b17023SJohn Marino 513*e4b17023SJohn Marino if (GET_CODE (reg) == SUBREG && REG_P (SUBREG_REG (reg))) 514*e4b17023SJohn Marino reg = SUBREG_REG (reg); 515*e4b17023SJohn Marino 516*e4b17023SJohn Marino if (STACK_REG_P (reg)) 517*e4b17023SJohn Marino { 518*e4b17023SJohn Marino clobber_reg[n_clobbers] = reg; 519*e4b17023SJohn Marino n_clobbers++; 520*e4b17023SJohn Marino } 521*e4b17023SJohn Marino } 522*e4b17023SJohn Marino } 523*e4b17023SJohn Marino 524*e4b17023SJohn Marino /* Enforce rule #4: Output operands must specifically indicate which 525*e4b17023SJohn Marino reg an output appears in after an asm. "=f" is not allowed: the 526*e4b17023SJohn Marino operand constraints must select a class with a single reg. 527*e4b17023SJohn Marino 528*e4b17023SJohn Marino Also enforce rule #5: Output operands must start at the top of 529*e4b17023SJohn Marino the reg-stack: output operands may not "skip" a reg. */ 530*e4b17023SJohn Marino 531*e4b17023SJohn Marino memset (reg_used_as_output, 0, sizeof (reg_used_as_output)); 532*e4b17023SJohn Marino for (i = 0; i < n_outputs; i++) 533*e4b17023SJohn Marino if (STACK_REG_P (recog_data.operand[i])) 534*e4b17023SJohn Marino { 535*e4b17023SJohn Marino if (reg_class_size[(int) recog_op_alt[i][alt].cl] != 1) 536*e4b17023SJohn Marino { 537*e4b17023SJohn Marino error_for_asm (insn, "output constraint %d must specify a single register", i); 538*e4b17023SJohn Marino malformed_asm = 1; 539*e4b17023SJohn Marino } 540*e4b17023SJohn Marino else 541*e4b17023SJohn Marino { 542*e4b17023SJohn Marino int j; 543*e4b17023SJohn Marino 544*e4b17023SJohn Marino for (j = 0; j < n_clobbers; j++) 545*e4b17023SJohn Marino if (REGNO (recog_data.operand[i]) == REGNO (clobber_reg[j])) 546*e4b17023SJohn Marino { 547*e4b17023SJohn Marino error_for_asm (insn, "output constraint %d cannot be specified together with \"%s\" clobber", 548*e4b17023SJohn Marino i, reg_names [REGNO (clobber_reg[j])]); 549*e4b17023SJohn Marino malformed_asm = 1; 550*e4b17023SJohn Marino break; 551*e4b17023SJohn Marino } 552*e4b17023SJohn Marino if (j == n_clobbers) 553*e4b17023SJohn Marino reg_used_as_output[REGNO (recog_data.operand[i])] = 1; 554*e4b17023SJohn Marino } 555*e4b17023SJohn Marino } 556*e4b17023SJohn Marino 557*e4b17023SJohn Marino 558*e4b17023SJohn Marino /* Search for first non-popped reg. */ 559*e4b17023SJohn Marino for (i = FIRST_STACK_REG; i < LAST_STACK_REG + 1; i++) 560*e4b17023SJohn Marino if (! reg_used_as_output[i]) 561*e4b17023SJohn Marino break; 562*e4b17023SJohn Marino 563*e4b17023SJohn Marino /* If there are any other popped regs, that's an error. */ 564*e4b17023SJohn Marino for (; i < LAST_STACK_REG + 1; i++) 565*e4b17023SJohn Marino if (reg_used_as_output[i]) 566*e4b17023SJohn Marino break; 567*e4b17023SJohn Marino 568*e4b17023SJohn Marino if (i != LAST_STACK_REG + 1) 569*e4b17023SJohn Marino { 570*e4b17023SJohn Marino error_for_asm (insn, "output regs must be grouped at top of stack"); 571*e4b17023SJohn Marino malformed_asm = 1; 572*e4b17023SJohn Marino } 573*e4b17023SJohn Marino 574*e4b17023SJohn Marino /* Enforce rule #2: All implicitly popped input regs must be closer 575*e4b17023SJohn Marino to the top of the reg-stack than any input that is not implicitly 576*e4b17023SJohn Marino popped. */ 577*e4b17023SJohn Marino 578*e4b17023SJohn Marino memset (implicitly_dies, 0, sizeof (implicitly_dies)); 579*e4b17023SJohn Marino for (i = n_outputs; i < n_outputs + n_inputs; i++) 580*e4b17023SJohn Marino if (STACK_REG_P (recog_data.operand[i])) 581*e4b17023SJohn Marino { 582*e4b17023SJohn Marino /* An input reg is implicitly popped if it is tied to an 583*e4b17023SJohn Marino output, or if there is a CLOBBER for it. */ 584*e4b17023SJohn Marino int j; 585*e4b17023SJohn Marino 586*e4b17023SJohn Marino for (j = 0; j < n_clobbers; j++) 587*e4b17023SJohn Marino if (operands_match_p (clobber_reg[j], recog_data.operand[i])) 588*e4b17023SJohn Marino break; 589*e4b17023SJohn Marino 590*e4b17023SJohn Marino if (j < n_clobbers || recog_op_alt[i][alt].matches >= 0) 591*e4b17023SJohn Marino implicitly_dies[REGNO (recog_data.operand[i])] = 1; 592*e4b17023SJohn Marino } 593*e4b17023SJohn Marino 594*e4b17023SJohn Marino /* Search for first non-popped reg. */ 595*e4b17023SJohn Marino for (i = FIRST_STACK_REG; i < LAST_STACK_REG + 1; i++) 596*e4b17023SJohn Marino if (! implicitly_dies[i]) 597*e4b17023SJohn Marino break; 598*e4b17023SJohn Marino 599*e4b17023SJohn Marino /* If there are any other popped regs, that's an error. */ 600*e4b17023SJohn Marino for (; i < LAST_STACK_REG + 1; i++) 601*e4b17023SJohn Marino if (implicitly_dies[i]) 602*e4b17023SJohn Marino break; 603*e4b17023SJohn Marino 604*e4b17023SJohn Marino if (i != LAST_STACK_REG + 1) 605*e4b17023SJohn Marino { 606*e4b17023SJohn Marino error_for_asm (insn, 607*e4b17023SJohn Marino "implicitly popped regs must be grouped at top of stack"); 608*e4b17023SJohn Marino malformed_asm = 1; 609*e4b17023SJohn Marino } 610*e4b17023SJohn Marino 611*e4b17023SJohn Marino /* Enforce rule #3: If any input operand uses the "f" constraint, all 612*e4b17023SJohn Marino output constraints must use the "&" earlyclobber. 613*e4b17023SJohn Marino 614*e4b17023SJohn Marino ??? Detect this more deterministically by having constrain_asm_operands 615*e4b17023SJohn Marino record any earlyclobber. */ 616*e4b17023SJohn Marino 617*e4b17023SJohn Marino for (i = n_outputs; i < n_outputs + n_inputs; i++) 618*e4b17023SJohn Marino if (recog_op_alt[i][alt].matches == -1) 619*e4b17023SJohn Marino { 620*e4b17023SJohn Marino int j; 621*e4b17023SJohn Marino 622*e4b17023SJohn Marino for (j = 0; j < n_outputs; j++) 623*e4b17023SJohn Marino if (operands_match_p (recog_data.operand[j], recog_data.operand[i])) 624*e4b17023SJohn Marino { 625*e4b17023SJohn Marino error_for_asm (insn, 626*e4b17023SJohn Marino "output operand %d must use %<&%> constraint", j); 627*e4b17023SJohn Marino malformed_asm = 1; 628*e4b17023SJohn Marino } 629*e4b17023SJohn Marino } 630*e4b17023SJohn Marino 631*e4b17023SJohn Marino if (malformed_asm) 632*e4b17023SJohn Marino { 633*e4b17023SJohn Marino /* Avoid further trouble with this insn. */ 634*e4b17023SJohn Marino PATTERN (insn) = gen_rtx_USE (VOIDmode, const0_rtx); 635*e4b17023SJohn Marino any_malformed_asm = true; 636*e4b17023SJohn Marino return 0; 637*e4b17023SJohn Marino } 638*e4b17023SJohn Marino 639*e4b17023SJohn Marino return 1; 640*e4b17023SJohn Marino } 641*e4b17023SJohn Marino 642*e4b17023SJohn Marino /* Calculate the number of inputs and outputs in BODY, an 643*e4b17023SJohn Marino asm_operands. N_OPERANDS is the total number of operands, and 644*e4b17023SJohn Marino N_INPUTS and N_OUTPUTS are pointers to ints into which the results are 645*e4b17023SJohn Marino placed. */ 646*e4b17023SJohn Marino 647*e4b17023SJohn Marino static void 648*e4b17023SJohn Marino get_asm_operands_in_out (rtx body, int *pout, int *pin) 649*e4b17023SJohn Marino { 650*e4b17023SJohn Marino rtx asmop = extract_asm_operands (body); 651*e4b17023SJohn Marino 652*e4b17023SJohn Marino *pin = ASM_OPERANDS_INPUT_LENGTH (asmop); 653*e4b17023SJohn Marino *pout = (recog_data.n_operands 654*e4b17023SJohn Marino - ASM_OPERANDS_INPUT_LENGTH (asmop) 655*e4b17023SJohn Marino - ASM_OPERANDS_LABEL_LENGTH (asmop)); 656*e4b17023SJohn Marino } 657*e4b17023SJohn Marino 658*e4b17023SJohn Marino /* If current function returns its result in an fp stack register, 659*e4b17023SJohn Marino return the REG. Otherwise, return 0. */ 660*e4b17023SJohn Marino 661*e4b17023SJohn Marino static rtx 662*e4b17023SJohn Marino stack_result (tree decl) 663*e4b17023SJohn Marino { 664*e4b17023SJohn Marino rtx result; 665*e4b17023SJohn Marino 666*e4b17023SJohn Marino /* If the value is supposed to be returned in memory, then clearly 667*e4b17023SJohn Marino it is not returned in a stack register. */ 668*e4b17023SJohn Marino if (aggregate_value_p (DECL_RESULT (decl), decl)) 669*e4b17023SJohn Marino return 0; 670*e4b17023SJohn Marino 671*e4b17023SJohn Marino result = DECL_RTL_IF_SET (DECL_RESULT (decl)); 672*e4b17023SJohn Marino if (result != 0) 673*e4b17023SJohn Marino result = targetm.calls.function_value (TREE_TYPE (DECL_RESULT (decl)), 674*e4b17023SJohn Marino decl, true); 675*e4b17023SJohn Marino 676*e4b17023SJohn Marino return result != 0 && STACK_REG_P (result) ? result : 0; 677*e4b17023SJohn Marino } 678*e4b17023SJohn Marino 679*e4b17023SJohn Marino 680*e4b17023SJohn Marino /* 681*e4b17023SJohn Marino * This section deals with stack register substitution, and forms the second 682*e4b17023SJohn Marino * pass over the RTL. 683*e4b17023SJohn Marino */ 684*e4b17023SJohn Marino 685*e4b17023SJohn Marino /* Replace REG, which is a pointer to a stack reg RTX, with an RTX for 686*e4b17023SJohn Marino the desired hard REGNO. */ 687*e4b17023SJohn Marino 688*e4b17023SJohn Marino static void 689*e4b17023SJohn Marino replace_reg (rtx *reg, int regno) 690*e4b17023SJohn Marino { 691*e4b17023SJohn Marino gcc_assert (IN_RANGE (regno, FIRST_STACK_REG, LAST_STACK_REG)); 692*e4b17023SJohn Marino gcc_assert (STACK_REG_P (*reg)); 693*e4b17023SJohn Marino 694*e4b17023SJohn Marino gcc_assert (SCALAR_FLOAT_MODE_P (GET_MODE (*reg)) 695*e4b17023SJohn Marino || GET_MODE_CLASS (GET_MODE (*reg)) == MODE_COMPLEX_FLOAT); 696*e4b17023SJohn Marino 697*e4b17023SJohn Marino *reg = FP_MODE_REG (regno, GET_MODE (*reg)); 698*e4b17023SJohn Marino } 699*e4b17023SJohn Marino 700*e4b17023SJohn Marino /* Remove a note of type NOTE, which must be found, for register 701*e4b17023SJohn Marino number REGNO from INSN. Remove only one such note. */ 702*e4b17023SJohn Marino 703*e4b17023SJohn Marino static void 704*e4b17023SJohn Marino remove_regno_note (rtx insn, enum reg_note note, unsigned int regno) 705*e4b17023SJohn Marino { 706*e4b17023SJohn Marino rtx *note_link, this_rtx; 707*e4b17023SJohn Marino 708*e4b17023SJohn Marino note_link = ®_NOTES (insn); 709*e4b17023SJohn Marino for (this_rtx = *note_link; this_rtx; this_rtx = XEXP (this_rtx, 1)) 710*e4b17023SJohn Marino if (REG_NOTE_KIND (this_rtx) == note 711*e4b17023SJohn Marino && REG_P (XEXP (this_rtx, 0)) && REGNO (XEXP (this_rtx, 0)) == regno) 712*e4b17023SJohn Marino { 713*e4b17023SJohn Marino *note_link = XEXP (this_rtx, 1); 714*e4b17023SJohn Marino return; 715*e4b17023SJohn Marino } 716*e4b17023SJohn Marino else 717*e4b17023SJohn Marino note_link = &XEXP (this_rtx, 1); 718*e4b17023SJohn Marino 719*e4b17023SJohn Marino gcc_unreachable (); 720*e4b17023SJohn Marino } 721*e4b17023SJohn Marino 722*e4b17023SJohn Marino /* Find the hard register number of virtual register REG in REGSTACK. 723*e4b17023SJohn Marino The hard register number is relative to the top of the stack. -1 is 724*e4b17023SJohn Marino returned if the register is not found. */ 725*e4b17023SJohn Marino 726*e4b17023SJohn Marino static int 727*e4b17023SJohn Marino get_hard_regnum (stack regstack, rtx reg) 728*e4b17023SJohn Marino { 729*e4b17023SJohn Marino int i; 730*e4b17023SJohn Marino 731*e4b17023SJohn Marino gcc_assert (STACK_REG_P (reg)); 732*e4b17023SJohn Marino 733*e4b17023SJohn Marino for (i = regstack->top; i >= 0; i--) 734*e4b17023SJohn Marino if (regstack->reg[i] == REGNO (reg)) 735*e4b17023SJohn Marino break; 736*e4b17023SJohn Marino 737*e4b17023SJohn Marino return i >= 0 ? (FIRST_STACK_REG + regstack->top - i) : -1; 738*e4b17023SJohn Marino } 739*e4b17023SJohn Marino 740*e4b17023SJohn Marino /* Emit an insn to pop virtual register REG before or after INSN. 741*e4b17023SJohn Marino REGSTACK is the stack state after INSN and is updated to reflect this 742*e4b17023SJohn Marino pop. WHEN is either emit_insn_before or emit_insn_after. A pop insn 743*e4b17023SJohn Marino is represented as a SET whose destination is the register to be popped 744*e4b17023SJohn Marino and source is the top of stack. A death note for the top of stack 745*e4b17023SJohn Marino cases the movdf pattern to pop. */ 746*e4b17023SJohn Marino 747*e4b17023SJohn Marino static rtx 748*e4b17023SJohn Marino emit_pop_insn (rtx insn, stack regstack, rtx reg, enum emit_where where) 749*e4b17023SJohn Marino { 750*e4b17023SJohn Marino rtx pop_insn, pop_rtx; 751*e4b17023SJohn Marino int hard_regno; 752*e4b17023SJohn Marino 753*e4b17023SJohn Marino /* For complex types take care to pop both halves. These may survive in 754*e4b17023SJohn Marino CLOBBER and USE expressions. */ 755*e4b17023SJohn Marino if (COMPLEX_MODE_P (GET_MODE (reg))) 756*e4b17023SJohn Marino { 757*e4b17023SJohn Marino rtx reg1 = FP_MODE_REG (REGNO (reg), DFmode); 758*e4b17023SJohn Marino rtx reg2 = FP_MODE_REG (REGNO (reg) + 1, DFmode); 759*e4b17023SJohn Marino 760*e4b17023SJohn Marino pop_insn = NULL_RTX; 761*e4b17023SJohn Marino if (get_hard_regnum (regstack, reg1) >= 0) 762*e4b17023SJohn Marino pop_insn = emit_pop_insn (insn, regstack, reg1, where); 763*e4b17023SJohn Marino if (get_hard_regnum (regstack, reg2) >= 0) 764*e4b17023SJohn Marino pop_insn = emit_pop_insn (insn, regstack, reg2, where); 765*e4b17023SJohn Marino gcc_assert (pop_insn); 766*e4b17023SJohn Marino return pop_insn; 767*e4b17023SJohn Marino } 768*e4b17023SJohn Marino 769*e4b17023SJohn Marino hard_regno = get_hard_regnum (regstack, reg); 770*e4b17023SJohn Marino 771*e4b17023SJohn Marino gcc_assert (hard_regno >= FIRST_STACK_REG); 772*e4b17023SJohn Marino 773*e4b17023SJohn Marino pop_rtx = gen_rtx_SET (VOIDmode, FP_MODE_REG (hard_regno, DFmode), 774*e4b17023SJohn Marino FP_MODE_REG (FIRST_STACK_REG, DFmode)); 775*e4b17023SJohn Marino 776*e4b17023SJohn Marino if (where == EMIT_AFTER) 777*e4b17023SJohn Marino pop_insn = emit_insn_after (pop_rtx, insn); 778*e4b17023SJohn Marino else 779*e4b17023SJohn Marino pop_insn = emit_insn_before (pop_rtx, insn); 780*e4b17023SJohn Marino 781*e4b17023SJohn Marino add_reg_note (pop_insn, REG_DEAD, FP_MODE_REG (FIRST_STACK_REG, DFmode)); 782*e4b17023SJohn Marino 783*e4b17023SJohn Marino regstack->reg[regstack->top - (hard_regno - FIRST_STACK_REG)] 784*e4b17023SJohn Marino = regstack->reg[regstack->top]; 785*e4b17023SJohn Marino regstack->top -= 1; 786*e4b17023SJohn Marino CLEAR_HARD_REG_BIT (regstack->reg_set, REGNO (reg)); 787*e4b17023SJohn Marino 788*e4b17023SJohn Marino return pop_insn; 789*e4b17023SJohn Marino } 790*e4b17023SJohn Marino 791*e4b17023SJohn Marino /* Emit an insn before or after INSN to swap virtual register REG with 792*e4b17023SJohn Marino the top of stack. REGSTACK is the stack state before the swap, and 793*e4b17023SJohn Marino is updated to reflect the swap. A swap insn is represented as a 794*e4b17023SJohn Marino PARALLEL of two patterns: each pattern moves one reg to the other. 795*e4b17023SJohn Marino 796*e4b17023SJohn Marino If REG is already at the top of the stack, no insn is emitted. */ 797*e4b17023SJohn Marino 798*e4b17023SJohn Marino static void 799*e4b17023SJohn Marino emit_swap_insn (rtx insn, stack regstack, rtx reg) 800*e4b17023SJohn Marino { 801*e4b17023SJohn Marino int hard_regno; 802*e4b17023SJohn Marino rtx swap_rtx; 803*e4b17023SJohn Marino int tmp, other_reg; /* swap regno temps */ 804*e4b17023SJohn Marino rtx i1; /* the stack-reg insn prior to INSN */ 805*e4b17023SJohn Marino rtx i1set = NULL_RTX; /* the SET rtx within I1 */ 806*e4b17023SJohn Marino 807*e4b17023SJohn Marino hard_regno = get_hard_regnum (regstack, reg); 808*e4b17023SJohn Marino 809*e4b17023SJohn Marino if (hard_regno == FIRST_STACK_REG) 810*e4b17023SJohn Marino return; 811*e4b17023SJohn Marino if (hard_regno == -1) 812*e4b17023SJohn Marino { 813*e4b17023SJohn Marino /* Something failed if the register wasn't on the stack. If we had 814*e4b17023SJohn Marino malformed asms, we zapped the instruction itself, but that didn't 815*e4b17023SJohn Marino produce the same pattern of register sets as before. To prevent 816*e4b17023SJohn Marino further failure, adjust REGSTACK to include REG at TOP. */ 817*e4b17023SJohn Marino gcc_assert (any_malformed_asm); 818*e4b17023SJohn Marino regstack->reg[++regstack->top] = REGNO (reg); 819*e4b17023SJohn Marino return; 820*e4b17023SJohn Marino } 821*e4b17023SJohn Marino gcc_assert (hard_regno >= FIRST_STACK_REG); 822*e4b17023SJohn Marino 823*e4b17023SJohn Marino other_reg = regstack->top - (hard_regno - FIRST_STACK_REG); 824*e4b17023SJohn Marino 825*e4b17023SJohn Marino tmp = regstack->reg[other_reg]; 826*e4b17023SJohn Marino regstack->reg[other_reg] = regstack->reg[regstack->top]; 827*e4b17023SJohn Marino regstack->reg[regstack->top] = tmp; 828*e4b17023SJohn Marino 829*e4b17023SJohn Marino /* Find the previous insn involving stack regs, but don't pass a 830*e4b17023SJohn Marino block boundary. */ 831*e4b17023SJohn Marino i1 = NULL; 832*e4b17023SJohn Marino if (current_block && insn != BB_HEAD (current_block)) 833*e4b17023SJohn Marino { 834*e4b17023SJohn Marino rtx tmp = PREV_INSN (insn); 835*e4b17023SJohn Marino rtx limit = PREV_INSN (BB_HEAD (current_block)); 836*e4b17023SJohn Marino while (tmp != limit) 837*e4b17023SJohn Marino { 838*e4b17023SJohn Marino if (LABEL_P (tmp) 839*e4b17023SJohn Marino || CALL_P (tmp) 840*e4b17023SJohn Marino || NOTE_INSN_BASIC_BLOCK_P (tmp) 841*e4b17023SJohn Marino || (NONJUMP_INSN_P (tmp) 842*e4b17023SJohn Marino && stack_regs_mentioned (tmp))) 843*e4b17023SJohn Marino { 844*e4b17023SJohn Marino i1 = tmp; 845*e4b17023SJohn Marino break; 846*e4b17023SJohn Marino } 847*e4b17023SJohn Marino tmp = PREV_INSN (tmp); 848*e4b17023SJohn Marino } 849*e4b17023SJohn Marino } 850*e4b17023SJohn Marino 851*e4b17023SJohn Marino if (i1 != NULL_RTX 852*e4b17023SJohn Marino && (i1set = single_set (i1)) != NULL_RTX) 853*e4b17023SJohn Marino { 854*e4b17023SJohn Marino rtx i1src = *get_true_reg (&SET_SRC (i1set)); 855*e4b17023SJohn Marino rtx i1dest = *get_true_reg (&SET_DEST (i1set)); 856*e4b17023SJohn Marino 857*e4b17023SJohn Marino /* If the previous register stack push was from the reg we are to 858*e4b17023SJohn Marino swap with, omit the swap. */ 859*e4b17023SJohn Marino 860*e4b17023SJohn Marino if (REG_P (i1dest) && REGNO (i1dest) == FIRST_STACK_REG 861*e4b17023SJohn Marino && REG_P (i1src) 862*e4b17023SJohn Marino && REGNO (i1src) == (unsigned) hard_regno - 1 863*e4b17023SJohn Marino && find_regno_note (i1, REG_DEAD, FIRST_STACK_REG) == NULL_RTX) 864*e4b17023SJohn Marino return; 865*e4b17023SJohn Marino 866*e4b17023SJohn Marino /* If the previous insn wrote to the reg we are to swap with, 867*e4b17023SJohn Marino omit the swap. */ 868*e4b17023SJohn Marino 869*e4b17023SJohn Marino if (REG_P (i1dest) && REGNO (i1dest) == (unsigned) hard_regno 870*e4b17023SJohn Marino && REG_P (i1src) && REGNO (i1src) == FIRST_STACK_REG 871*e4b17023SJohn Marino && find_regno_note (i1, REG_DEAD, FIRST_STACK_REG) == NULL_RTX) 872*e4b17023SJohn Marino return; 873*e4b17023SJohn Marino } 874*e4b17023SJohn Marino 875*e4b17023SJohn Marino /* Avoid emitting the swap if this is the first register stack insn 876*e4b17023SJohn Marino of the current_block. Instead update the current_block's stack_in 877*e4b17023SJohn Marino and let compensate edges take care of this for us. */ 878*e4b17023SJohn Marino if (current_block && starting_stack_p) 879*e4b17023SJohn Marino { 880*e4b17023SJohn Marino BLOCK_INFO (current_block)->stack_in = *regstack; 881*e4b17023SJohn Marino starting_stack_p = false; 882*e4b17023SJohn Marino return; 883*e4b17023SJohn Marino } 884*e4b17023SJohn Marino 885*e4b17023SJohn Marino swap_rtx = gen_swapxf (FP_MODE_REG (hard_regno, XFmode), 886*e4b17023SJohn Marino FP_MODE_REG (FIRST_STACK_REG, XFmode)); 887*e4b17023SJohn Marino 888*e4b17023SJohn Marino if (i1) 889*e4b17023SJohn Marino emit_insn_after (swap_rtx, i1); 890*e4b17023SJohn Marino else if (current_block) 891*e4b17023SJohn Marino emit_insn_before (swap_rtx, BB_HEAD (current_block)); 892*e4b17023SJohn Marino else 893*e4b17023SJohn Marino emit_insn_before (swap_rtx, insn); 894*e4b17023SJohn Marino } 895*e4b17023SJohn Marino 896*e4b17023SJohn Marino /* Emit an insns before INSN to swap virtual register SRC1 with 897*e4b17023SJohn Marino the top of stack and virtual register SRC2 with second stack 898*e4b17023SJohn Marino slot. REGSTACK is the stack state before the swaps, and 899*e4b17023SJohn Marino is updated to reflect the swaps. A swap insn is represented as a 900*e4b17023SJohn Marino PARALLEL of two patterns: each pattern moves one reg to the other. 901*e4b17023SJohn Marino 902*e4b17023SJohn Marino If SRC1 and/or SRC2 are already at the right place, no swap insn 903*e4b17023SJohn Marino is emitted. */ 904*e4b17023SJohn Marino 905*e4b17023SJohn Marino static void 906*e4b17023SJohn Marino swap_to_top (rtx insn, stack regstack, rtx src1, rtx src2) 907*e4b17023SJohn Marino { 908*e4b17023SJohn Marino struct stack_def temp_stack; 909*e4b17023SJohn Marino int regno, j, k, temp; 910*e4b17023SJohn Marino 911*e4b17023SJohn Marino temp_stack = *regstack; 912*e4b17023SJohn Marino 913*e4b17023SJohn Marino /* Place operand 1 at the top of stack. */ 914*e4b17023SJohn Marino regno = get_hard_regnum (&temp_stack, src1); 915*e4b17023SJohn Marino gcc_assert (regno >= 0); 916*e4b17023SJohn Marino if (regno != FIRST_STACK_REG) 917*e4b17023SJohn Marino { 918*e4b17023SJohn Marino k = temp_stack.top - (regno - FIRST_STACK_REG); 919*e4b17023SJohn Marino j = temp_stack.top; 920*e4b17023SJohn Marino 921*e4b17023SJohn Marino temp = temp_stack.reg[k]; 922*e4b17023SJohn Marino temp_stack.reg[k] = temp_stack.reg[j]; 923*e4b17023SJohn Marino temp_stack.reg[j] = temp; 924*e4b17023SJohn Marino } 925*e4b17023SJohn Marino 926*e4b17023SJohn Marino /* Place operand 2 next on the stack. */ 927*e4b17023SJohn Marino regno = get_hard_regnum (&temp_stack, src2); 928*e4b17023SJohn Marino gcc_assert (regno >= 0); 929*e4b17023SJohn Marino if (regno != FIRST_STACK_REG + 1) 930*e4b17023SJohn Marino { 931*e4b17023SJohn Marino k = temp_stack.top - (regno - FIRST_STACK_REG); 932*e4b17023SJohn Marino j = temp_stack.top - 1; 933*e4b17023SJohn Marino 934*e4b17023SJohn Marino temp = temp_stack.reg[k]; 935*e4b17023SJohn Marino temp_stack.reg[k] = temp_stack.reg[j]; 936*e4b17023SJohn Marino temp_stack.reg[j] = temp; 937*e4b17023SJohn Marino } 938*e4b17023SJohn Marino 939*e4b17023SJohn Marino change_stack (insn, regstack, &temp_stack, EMIT_BEFORE); 940*e4b17023SJohn Marino } 941*e4b17023SJohn Marino 942*e4b17023SJohn Marino /* Handle a move to or from a stack register in PAT, which is in INSN. 943*e4b17023SJohn Marino REGSTACK is the current stack. Return whether a control flow insn 944*e4b17023SJohn Marino was deleted in the process. */ 945*e4b17023SJohn Marino 946*e4b17023SJohn Marino static bool 947*e4b17023SJohn Marino move_for_stack_reg (rtx insn, stack regstack, rtx pat) 948*e4b17023SJohn Marino { 949*e4b17023SJohn Marino rtx *psrc = get_true_reg (&SET_SRC (pat)); 950*e4b17023SJohn Marino rtx *pdest = get_true_reg (&SET_DEST (pat)); 951*e4b17023SJohn Marino rtx src, dest; 952*e4b17023SJohn Marino rtx note; 953*e4b17023SJohn Marino bool control_flow_insn_deleted = false; 954*e4b17023SJohn Marino 955*e4b17023SJohn Marino src = *psrc; dest = *pdest; 956*e4b17023SJohn Marino 957*e4b17023SJohn Marino if (STACK_REG_P (src) && STACK_REG_P (dest)) 958*e4b17023SJohn Marino { 959*e4b17023SJohn Marino /* Write from one stack reg to another. If SRC dies here, then 960*e4b17023SJohn Marino just change the register mapping and delete the insn. */ 961*e4b17023SJohn Marino 962*e4b17023SJohn Marino note = find_regno_note (insn, REG_DEAD, REGNO (src)); 963*e4b17023SJohn Marino if (note) 964*e4b17023SJohn Marino { 965*e4b17023SJohn Marino int i; 966*e4b17023SJohn Marino 967*e4b17023SJohn Marino /* If this is a no-op move, there must not be a REG_DEAD note. */ 968*e4b17023SJohn Marino gcc_assert (REGNO (src) != REGNO (dest)); 969*e4b17023SJohn Marino 970*e4b17023SJohn Marino for (i = regstack->top; i >= 0; i--) 971*e4b17023SJohn Marino if (regstack->reg[i] == REGNO (src)) 972*e4b17023SJohn Marino break; 973*e4b17023SJohn Marino 974*e4b17023SJohn Marino /* The destination must be dead, or life analysis is borked. */ 975*e4b17023SJohn Marino gcc_assert (get_hard_regnum (regstack, dest) < FIRST_STACK_REG); 976*e4b17023SJohn Marino 977*e4b17023SJohn Marino /* If the source is not live, this is yet another case of 978*e4b17023SJohn Marino uninitialized variables. Load up a NaN instead. */ 979*e4b17023SJohn Marino if (i < 0) 980*e4b17023SJohn Marino return move_nan_for_stack_reg (insn, regstack, dest); 981*e4b17023SJohn Marino 982*e4b17023SJohn Marino /* It is possible that the dest is unused after this insn. 983*e4b17023SJohn Marino If so, just pop the src. */ 984*e4b17023SJohn Marino 985*e4b17023SJohn Marino if (find_regno_note (insn, REG_UNUSED, REGNO (dest))) 986*e4b17023SJohn Marino emit_pop_insn (insn, regstack, src, EMIT_AFTER); 987*e4b17023SJohn Marino else 988*e4b17023SJohn Marino { 989*e4b17023SJohn Marino regstack->reg[i] = REGNO (dest); 990*e4b17023SJohn Marino SET_HARD_REG_BIT (regstack->reg_set, REGNO (dest)); 991*e4b17023SJohn Marino CLEAR_HARD_REG_BIT (regstack->reg_set, REGNO (src)); 992*e4b17023SJohn Marino } 993*e4b17023SJohn Marino 994*e4b17023SJohn Marino control_flow_insn_deleted |= control_flow_insn_p (insn); 995*e4b17023SJohn Marino delete_insn (insn); 996*e4b17023SJohn Marino return control_flow_insn_deleted; 997*e4b17023SJohn Marino } 998*e4b17023SJohn Marino 999*e4b17023SJohn Marino /* The source reg does not die. */ 1000*e4b17023SJohn Marino 1001*e4b17023SJohn Marino /* If this appears to be a no-op move, delete it, or else it 1002*e4b17023SJohn Marino will confuse the machine description output patterns. But if 1003*e4b17023SJohn Marino it is REG_UNUSED, we must pop the reg now, as per-insn processing 1004*e4b17023SJohn Marino for REG_UNUSED will not work for deleted insns. */ 1005*e4b17023SJohn Marino 1006*e4b17023SJohn Marino if (REGNO (src) == REGNO (dest)) 1007*e4b17023SJohn Marino { 1008*e4b17023SJohn Marino if (find_regno_note (insn, REG_UNUSED, REGNO (dest))) 1009*e4b17023SJohn Marino emit_pop_insn (insn, regstack, dest, EMIT_AFTER); 1010*e4b17023SJohn Marino 1011*e4b17023SJohn Marino control_flow_insn_deleted |= control_flow_insn_p (insn); 1012*e4b17023SJohn Marino delete_insn (insn); 1013*e4b17023SJohn Marino return control_flow_insn_deleted; 1014*e4b17023SJohn Marino } 1015*e4b17023SJohn Marino 1016*e4b17023SJohn Marino /* The destination ought to be dead. */ 1017*e4b17023SJohn Marino gcc_assert (get_hard_regnum (regstack, dest) < FIRST_STACK_REG); 1018*e4b17023SJohn Marino 1019*e4b17023SJohn Marino replace_reg (psrc, get_hard_regnum (regstack, src)); 1020*e4b17023SJohn Marino 1021*e4b17023SJohn Marino regstack->reg[++regstack->top] = REGNO (dest); 1022*e4b17023SJohn Marino SET_HARD_REG_BIT (regstack->reg_set, REGNO (dest)); 1023*e4b17023SJohn Marino replace_reg (pdest, FIRST_STACK_REG); 1024*e4b17023SJohn Marino } 1025*e4b17023SJohn Marino else if (STACK_REG_P (src)) 1026*e4b17023SJohn Marino { 1027*e4b17023SJohn Marino /* Save from a stack reg to MEM, or possibly integer reg. Since 1028*e4b17023SJohn Marino only top of stack may be saved, emit an exchange first if 1029*e4b17023SJohn Marino needs be. */ 1030*e4b17023SJohn Marino 1031*e4b17023SJohn Marino emit_swap_insn (insn, regstack, src); 1032*e4b17023SJohn Marino 1033*e4b17023SJohn Marino note = find_regno_note (insn, REG_DEAD, REGNO (src)); 1034*e4b17023SJohn Marino if (note) 1035*e4b17023SJohn Marino { 1036*e4b17023SJohn Marino replace_reg (&XEXP (note, 0), FIRST_STACK_REG); 1037*e4b17023SJohn Marino regstack->top--; 1038*e4b17023SJohn Marino CLEAR_HARD_REG_BIT (regstack->reg_set, REGNO (src)); 1039*e4b17023SJohn Marino } 1040*e4b17023SJohn Marino else if ((GET_MODE (src) == XFmode) 1041*e4b17023SJohn Marino && regstack->top < REG_STACK_SIZE - 1) 1042*e4b17023SJohn Marino { 1043*e4b17023SJohn Marino /* A 387 cannot write an XFmode value to a MEM without 1044*e4b17023SJohn Marino clobbering the source reg. The output code can handle 1045*e4b17023SJohn Marino this by reading back the value from the MEM. 1046*e4b17023SJohn Marino But it is more efficient to use a temp register if one is 1047*e4b17023SJohn Marino available. Push the source value here if the register 1048*e4b17023SJohn Marino stack is not full, and then write the value to memory via 1049*e4b17023SJohn Marino a pop. */ 1050*e4b17023SJohn Marino rtx push_rtx; 1051*e4b17023SJohn Marino rtx top_stack_reg = FP_MODE_REG (FIRST_STACK_REG, GET_MODE (src)); 1052*e4b17023SJohn Marino 1053*e4b17023SJohn Marino push_rtx = gen_movxf (top_stack_reg, top_stack_reg); 1054*e4b17023SJohn Marino emit_insn_before (push_rtx, insn); 1055*e4b17023SJohn Marino add_reg_note (insn, REG_DEAD, top_stack_reg); 1056*e4b17023SJohn Marino } 1057*e4b17023SJohn Marino 1058*e4b17023SJohn Marino replace_reg (psrc, FIRST_STACK_REG); 1059*e4b17023SJohn Marino } 1060*e4b17023SJohn Marino else 1061*e4b17023SJohn Marino { 1062*e4b17023SJohn Marino rtx pat = PATTERN (insn); 1063*e4b17023SJohn Marino 1064*e4b17023SJohn Marino gcc_assert (STACK_REG_P (dest)); 1065*e4b17023SJohn Marino 1066*e4b17023SJohn Marino /* Load from MEM, or possibly integer REG or constant, into the 1067*e4b17023SJohn Marino stack regs. The actual target is always the top of the 1068*e4b17023SJohn Marino stack. The stack mapping is changed to reflect that DEST is 1069*e4b17023SJohn Marino now at top of stack. */ 1070*e4b17023SJohn Marino 1071*e4b17023SJohn Marino /* The destination ought to be dead. However, there is a 1072*e4b17023SJohn Marino special case with i387 UNSPEC_TAN, where destination is live 1073*e4b17023SJohn Marino (an argument to fptan) but inherent load of 1.0 is modelled 1074*e4b17023SJohn Marino as a load from a constant. */ 1075*e4b17023SJohn Marino if (GET_CODE (pat) == PARALLEL 1076*e4b17023SJohn Marino && XVECLEN (pat, 0) == 2 1077*e4b17023SJohn Marino && GET_CODE (XVECEXP (pat, 0, 1)) == SET 1078*e4b17023SJohn Marino && GET_CODE (SET_SRC (XVECEXP (pat, 0, 1))) == UNSPEC 1079*e4b17023SJohn Marino && XINT (SET_SRC (XVECEXP (pat, 0, 1)), 1) == UNSPEC_TAN) 1080*e4b17023SJohn Marino emit_swap_insn (insn, regstack, dest); 1081*e4b17023SJohn Marino else 1082*e4b17023SJohn Marino gcc_assert (get_hard_regnum (regstack, dest) < FIRST_STACK_REG); 1083*e4b17023SJohn Marino 1084*e4b17023SJohn Marino gcc_assert (regstack->top < REG_STACK_SIZE); 1085*e4b17023SJohn Marino 1086*e4b17023SJohn Marino regstack->reg[++regstack->top] = REGNO (dest); 1087*e4b17023SJohn Marino SET_HARD_REG_BIT (regstack->reg_set, REGNO (dest)); 1088*e4b17023SJohn Marino replace_reg (pdest, FIRST_STACK_REG); 1089*e4b17023SJohn Marino } 1090*e4b17023SJohn Marino 1091*e4b17023SJohn Marino return control_flow_insn_deleted; 1092*e4b17023SJohn Marino } 1093*e4b17023SJohn Marino 1094*e4b17023SJohn Marino /* A helper function which replaces INSN with a pattern that loads up 1095*e4b17023SJohn Marino a NaN into DEST, then invokes move_for_stack_reg. */ 1096*e4b17023SJohn Marino 1097*e4b17023SJohn Marino static bool 1098*e4b17023SJohn Marino move_nan_for_stack_reg (rtx insn, stack regstack, rtx dest) 1099*e4b17023SJohn Marino { 1100*e4b17023SJohn Marino rtx pat; 1101*e4b17023SJohn Marino 1102*e4b17023SJohn Marino dest = FP_MODE_REG (REGNO (dest), SFmode); 1103*e4b17023SJohn Marino pat = gen_rtx_SET (VOIDmode, dest, not_a_num); 1104*e4b17023SJohn Marino PATTERN (insn) = pat; 1105*e4b17023SJohn Marino INSN_CODE (insn) = -1; 1106*e4b17023SJohn Marino 1107*e4b17023SJohn Marino return move_for_stack_reg (insn, regstack, pat); 1108*e4b17023SJohn Marino } 1109*e4b17023SJohn Marino 1110*e4b17023SJohn Marino /* Swap the condition on a branch, if there is one. Return true if we 1111*e4b17023SJohn Marino found a condition to swap. False if the condition was not used as 1112*e4b17023SJohn Marino such. */ 1113*e4b17023SJohn Marino 1114*e4b17023SJohn Marino static int 1115*e4b17023SJohn Marino swap_rtx_condition_1 (rtx pat) 1116*e4b17023SJohn Marino { 1117*e4b17023SJohn Marino const char *fmt; 1118*e4b17023SJohn Marino int i, r = 0; 1119*e4b17023SJohn Marino 1120*e4b17023SJohn Marino if (COMPARISON_P (pat)) 1121*e4b17023SJohn Marino { 1122*e4b17023SJohn Marino PUT_CODE (pat, swap_condition (GET_CODE (pat))); 1123*e4b17023SJohn Marino r = 1; 1124*e4b17023SJohn Marino } 1125*e4b17023SJohn Marino else 1126*e4b17023SJohn Marino { 1127*e4b17023SJohn Marino fmt = GET_RTX_FORMAT (GET_CODE (pat)); 1128*e4b17023SJohn Marino for (i = GET_RTX_LENGTH (GET_CODE (pat)) - 1; i >= 0; i--) 1129*e4b17023SJohn Marino { 1130*e4b17023SJohn Marino if (fmt[i] == 'E') 1131*e4b17023SJohn Marino { 1132*e4b17023SJohn Marino int j; 1133*e4b17023SJohn Marino 1134*e4b17023SJohn Marino for (j = XVECLEN (pat, i) - 1; j >= 0; j--) 1135*e4b17023SJohn Marino r |= swap_rtx_condition_1 (XVECEXP (pat, i, j)); 1136*e4b17023SJohn Marino } 1137*e4b17023SJohn Marino else if (fmt[i] == 'e') 1138*e4b17023SJohn Marino r |= swap_rtx_condition_1 (XEXP (pat, i)); 1139*e4b17023SJohn Marino } 1140*e4b17023SJohn Marino } 1141*e4b17023SJohn Marino 1142*e4b17023SJohn Marino return r; 1143*e4b17023SJohn Marino } 1144*e4b17023SJohn Marino 1145*e4b17023SJohn Marino static int 1146*e4b17023SJohn Marino swap_rtx_condition (rtx insn) 1147*e4b17023SJohn Marino { 1148*e4b17023SJohn Marino rtx pat = PATTERN (insn); 1149*e4b17023SJohn Marino 1150*e4b17023SJohn Marino /* We're looking for a single set to cc0 or an HImode temporary. */ 1151*e4b17023SJohn Marino 1152*e4b17023SJohn Marino if (GET_CODE (pat) == SET 1153*e4b17023SJohn Marino && REG_P (SET_DEST (pat)) 1154*e4b17023SJohn Marino && REGNO (SET_DEST (pat)) == FLAGS_REG) 1155*e4b17023SJohn Marino { 1156*e4b17023SJohn Marino insn = next_flags_user (insn); 1157*e4b17023SJohn Marino if (insn == NULL_RTX) 1158*e4b17023SJohn Marino return 0; 1159*e4b17023SJohn Marino pat = PATTERN (insn); 1160*e4b17023SJohn Marino } 1161*e4b17023SJohn Marino 1162*e4b17023SJohn Marino /* See if this is, or ends in, a fnstsw. If so, we're not doing anything 1163*e4b17023SJohn Marino with the cc value right now. We may be able to search for one 1164*e4b17023SJohn Marino though. */ 1165*e4b17023SJohn Marino 1166*e4b17023SJohn Marino if (GET_CODE (pat) == SET 1167*e4b17023SJohn Marino && GET_CODE (SET_SRC (pat)) == UNSPEC 1168*e4b17023SJohn Marino && XINT (SET_SRC (pat), 1) == UNSPEC_FNSTSW) 1169*e4b17023SJohn Marino { 1170*e4b17023SJohn Marino rtx dest = SET_DEST (pat); 1171*e4b17023SJohn Marino 1172*e4b17023SJohn Marino /* Search forward looking for the first use of this value. 1173*e4b17023SJohn Marino Stop at block boundaries. */ 1174*e4b17023SJohn Marino while (insn != BB_END (current_block)) 1175*e4b17023SJohn Marino { 1176*e4b17023SJohn Marino insn = NEXT_INSN (insn); 1177*e4b17023SJohn Marino if (INSN_P (insn) && reg_mentioned_p (dest, insn)) 1178*e4b17023SJohn Marino break; 1179*e4b17023SJohn Marino if (CALL_P (insn)) 1180*e4b17023SJohn Marino return 0; 1181*e4b17023SJohn Marino } 1182*e4b17023SJohn Marino 1183*e4b17023SJohn Marino /* We haven't found it. */ 1184*e4b17023SJohn Marino if (insn == BB_END (current_block)) 1185*e4b17023SJohn Marino return 0; 1186*e4b17023SJohn Marino 1187*e4b17023SJohn Marino /* So we've found the insn using this value. If it is anything 1188*e4b17023SJohn Marino other than sahf or the value does not die (meaning we'd have 1189*e4b17023SJohn Marino to search further), then we must give up. */ 1190*e4b17023SJohn Marino pat = PATTERN (insn); 1191*e4b17023SJohn Marino if (GET_CODE (pat) != SET 1192*e4b17023SJohn Marino || GET_CODE (SET_SRC (pat)) != UNSPEC 1193*e4b17023SJohn Marino || XINT (SET_SRC (pat), 1) != UNSPEC_SAHF 1194*e4b17023SJohn Marino || ! dead_or_set_p (insn, dest)) 1195*e4b17023SJohn Marino return 0; 1196*e4b17023SJohn Marino 1197*e4b17023SJohn Marino /* Now we are prepared to handle this as a normal cc0 setter. */ 1198*e4b17023SJohn Marino insn = next_flags_user (insn); 1199*e4b17023SJohn Marino if (insn == NULL_RTX) 1200*e4b17023SJohn Marino return 0; 1201*e4b17023SJohn Marino pat = PATTERN (insn); 1202*e4b17023SJohn Marino } 1203*e4b17023SJohn Marino 1204*e4b17023SJohn Marino if (swap_rtx_condition_1 (pat)) 1205*e4b17023SJohn Marino { 1206*e4b17023SJohn Marino int fail = 0; 1207*e4b17023SJohn Marino INSN_CODE (insn) = -1; 1208*e4b17023SJohn Marino if (recog_memoized (insn) == -1) 1209*e4b17023SJohn Marino fail = 1; 1210*e4b17023SJohn Marino /* In case the flags don't die here, recurse to try fix 1211*e4b17023SJohn Marino following user too. */ 1212*e4b17023SJohn Marino else if (! dead_or_set_p (insn, ix86_flags_rtx)) 1213*e4b17023SJohn Marino { 1214*e4b17023SJohn Marino insn = next_flags_user (insn); 1215*e4b17023SJohn Marino if (!insn || !swap_rtx_condition (insn)) 1216*e4b17023SJohn Marino fail = 1; 1217*e4b17023SJohn Marino } 1218*e4b17023SJohn Marino if (fail) 1219*e4b17023SJohn Marino { 1220*e4b17023SJohn Marino swap_rtx_condition_1 (pat); 1221*e4b17023SJohn Marino return 0; 1222*e4b17023SJohn Marino } 1223*e4b17023SJohn Marino return 1; 1224*e4b17023SJohn Marino } 1225*e4b17023SJohn Marino return 0; 1226*e4b17023SJohn Marino } 1227*e4b17023SJohn Marino 1228*e4b17023SJohn Marino /* Handle a comparison. Special care needs to be taken to avoid 1229*e4b17023SJohn Marino causing comparisons that a 387 cannot do correctly, such as EQ. 1230*e4b17023SJohn Marino 1231*e4b17023SJohn Marino Also, a pop insn may need to be emitted. The 387 does have an 1232*e4b17023SJohn Marino `fcompp' insn that can pop two regs, but it is sometimes too expensive 1233*e4b17023SJohn Marino to do this - a `fcomp' followed by a `fstpl %st(0)' may be easier to 1234*e4b17023SJohn Marino set up. */ 1235*e4b17023SJohn Marino 1236*e4b17023SJohn Marino static void 1237*e4b17023SJohn Marino compare_for_stack_reg (rtx insn, stack regstack, rtx pat_src) 1238*e4b17023SJohn Marino { 1239*e4b17023SJohn Marino rtx *src1, *src2; 1240*e4b17023SJohn Marino rtx src1_note, src2_note; 1241*e4b17023SJohn Marino 1242*e4b17023SJohn Marino src1 = get_true_reg (&XEXP (pat_src, 0)); 1243*e4b17023SJohn Marino src2 = get_true_reg (&XEXP (pat_src, 1)); 1244*e4b17023SJohn Marino 1245*e4b17023SJohn Marino /* ??? If fxch turns out to be cheaper than fstp, give priority to 1246*e4b17023SJohn Marino registers that die in this insn - move those to stack top first. */ 1247*e4b17023SJohn Marino if ((! STACK_REG_P (*src1) 1248*e4b17023SJohn Marino || (STACK_REG_P (*src2) 1249*e4b17023SJohn Marino && get_hard_regnum (regstack, *src2) == FIRST_STACK_REG)) 1250*e4b17023SJohn Marino && swap_rtx_condition (insn)) 1251*e4b17023SJohn Marino { 1252*e4b17023SJohn Marino rtx temp; 1253*e4b17023SJohn Marino temp = XEXP (pat_src, 0); 1254*e4b17023SJohn Marino XEXP (pat_src, 0) = XEXP (pat_src, 1); 1255*e4b17023SJohn Marino XEXP (pat_src, 1) = temp; 1256*e4b17023SJohn Marino 1257*e4b17023SJohn Marino src1 = get_true_reg (&XEXP (pat_src, 0)); 1258*e4b17023SJohn Marino src2 = get_true_reg (&XEXP (pat_src, 1)); 1259*e4b17023SJohn Marino 1260*e4b17023SJohn Marino INSN_CODE (insn) = -1; 1261*e4b17023SJohn Marino } 1262*e4b17023SJohn Marino 1263*e4b17023SJohn Marino /* We will fix any death note later. */ 1264*e4b17023SJohn Marino 1265*e4b17023SJohn Marino src1_note = find_regno_note (insn, REG_DEAD, REGNO (*src1)); 1266*e4b17023SJohn Marino 1267*e4b17023SJohn Marino if (STACK_REG_P (*src2)) 1268*e4b17023SJohn Marino src2_note = find_regno_note (insn, REG_DEAD, REGNO (*src2)); 1269*e4b17023SJohn Marino else 1270*e4b17023SJohn Marino src2_note = NULL_RTX; 1271*e4b17023SJohn Marino 1272*e4b17023SJohn Marino emit_swap_insn (insn, regstack, *src1); 1273*e4b17023SJohn Marino 1274*e4b17023SJohn Marino replace_reg (src1, FIRST_STACK_REG); 1275*e4b17023SJohn Marino 1276*e4b17023SJohn Marino if (STACK_REG_P (*src2)) 1277*e4b17023SJohn Marino replace_reg (src2, get_hard_regnum (regstack, *src2)); 1278*e4b17023SJohn Marino 1279*e4b17023SJohn Marino if (src1_note) 1280*e4b17023SJohn Marino { 1281*e4b17023SJohn Marino pop_stack (regstack, REGNO (XEXP (src1_note, 0))); 1282*e4b17023SJohn Marino replace_reg (&XEXP (src1_note, 0), FIRST_STACK_REG); 1283*e4b17023SJohn Marino } 1284*e4b17023SJohn Marino 1285*e4b17023SJohn Marino /* If the second operand dies, handle that. But if the operands are 1286*e4b17023SJohn Marino the same stack register, don't bother, because only one death is 1287*e4b17023SJohn Marino needed, and it was just handled. */ 1288*e4b17023SJohn Marino 1289*e4b17023SJohn Marino if (src2_note 1290*e4b17023SJohn Marino && ! (STACK_REG_P (*src1) && STACK_REG_P (*src2) 1291*e4b17023SJohn Marino && REGNO (*src1) == REGNO (*src2))) 1292*e4b17023SJohn Marino { 1293*e4b17023SJohn Marino /* As a special case, two regs may die in this insn if src2 is 1294*e4b17023SJohn Marino next to top of stack and the top of stack also dies. Since 1295*e4b17023SJohn Marino we have already popped src1, "next to top of stack" is really 1296*e4b17023SJohn Marino at top (FIRST_STACK_REG) now. */ 1297*e4b17023SJohn Marino 1298*e4b17023SJohn Marino if (get_hard_regnum (regstack, XEXP (src2_note, 0)) == FIRST_STACK_REG 1299*e4b17023SJohn Marino && src1_note) 1300*e4b17023SJohn Marino { 1301*e4b17023SJohn Marino pop_stack (regstack, REGNO (XEXP (src2_note, 0))); 1302*e4b17023SJohn Marino replace_reg (&XEXP (src2_note, 0), FIRST_STACK_REG + 1); 1303*e4b17023SJohn Marino } 1304*e4b17023SJohn Marino else 1305*e4b17023SJohn Marino { 1306*e4b17023SJohn Marino /* The 386 can only represent death of the first operand in 1307*e4b17023SJohn Marino the case handled above. In all other cases, emit a separate 1308*e4b17023SJohn Marino pop and remove the death note from here. */ 1309*e4b17023SJohn Marino 1310*e4b17023SJohn Marino /* link_cc0_insns (insn); */ 1311*e4b17023SJohn Marino 1312*e4b17023SJohn Marino remove_regno_note (insn, REG_DEAD, REGNO (XEXP (src2_note, 0))); 1313*e4b17023SJohn Marino 1314*e4b17023SJohn Marino emit_pop_insn (insn, regstack, XEXP (src2_note, 0), 1315*e4b17023SJohn Marino EMIT_AFTER); 1316*e4b17023SJohn Marino } 1317*e4b17023SJohn Marino } 1318*e4b17023SJohn Marino } 1319*e4b17023SJohn Marino 1320*e4b17023SJohn Marino /* Substitute new registers in LOC, which is part of a debug insn. 1321*e4b17023SJohn Marino REGSTACK is the current register layout. */ 1322*e4b17023SJohn Marino 1323*e4b17023SJohn Marino static int 1324*e4b17023SJohn Marino subst_stack_regs_in_debug_insn (rtx *loc, void *data) 1325*e4b17023SJohn Marino { 1326*e4b17023SJohn Marino stack regstack = (stack)data; 1327*e4b17023SJohn Marino int hard_regno; 1328*e4b17023SJohn Marino 1329*e4b17023SJohn Marino if (!STACK_REG_P (*loc)) 1330*e4b17023SJohn Marino return 0; 1331*e4b17023SJohn Marino 1332*e4b17023SJohn Marino hard_regno = get_hard_regnum (regstack, *loc); 1333*e4b17023SJohn Marino 1334*e4b17023SJohn Marino /* If we can't find an active register, reset this debug insn. */ 1335*e4b17023SJohn Marino if (hard_regno == -1) 1336*e4b17023SJohn Marino return 1; 1337*e4b17023SJohn Marino 1338*e4b17023SJohn Marino gcc_assert (hard_regno >= FIRST_STACK_REG); 1339*e4b17023SJohn Marino 1340*e4b17023SJohn Marino replace_reg (loc, hard_regno); 1341*e4b17023SJohn Marino 1342*e4b17023SJohn Marino return -1; 1343*e4b17023SJohn Marino } 1344*e4b17023SJohn Marino 1345*e4b17023SJohn Marino /* Substitute hardware stack regs in debug insn INSN, using stack 1346*e4b17023SJohn Marino layout REGSTACK. If we can't find a hardware stack reg for any of 1347*e4b17023SJohn Marino the REGs in it, reset the debug insn. */ 1348*e4b17023SJohn Marino 1349*e4b17023SJohn Marino static void 1350*e4b17023SJohn Marino subst_all_stack_regs_in_debug_insn (rtx insn, struct stack_def *regstack) 1351*e4b17023SJohn Marino { 1352*e4b17023SJohn Marino int ret = for_each_rtx (&INSN_VAR_LOCATION_LOC (insn), 1353*e4b17023SJohn Marino subst_stack_regs_in_debug_insn, 1354*e4b17023SJohn Marino regstack); 1355*e4b17023SJohn Marino 1356*e4b17023SJohn Marino if (ret == 1) 1357*e4b17023SJohn Marino INSN_VAR_LOCATION_LOC (insn) = gen_rtx_UNKNOWN_VAR_LOC (); 1358*e4b17023SJohn Marino else 1359*e4b17023SJohn Marino gcc_checking_assert (ret == 0); 1360*e4b17023SJohn Marino } 1361*e4b17023SJohn Marino 1362*e4b17023SJohn Marino /* Substitute new registers in PAT, which is part of INSN. REGSTACK 1363*e4b17023SJohn Marino is the current register layout. Return whether a control flow insn 1364*e4b17023SJohn Marino was deleted in the process. */ 1365*e4b17023SJohn Marino 1366*e4b17023SJohn Marino static bool 1367*e4b17023SJohn Marino subst_stack_regs_pat (rtx insn, stack regstack, rtx pat) 1368*e4b17023SJohn Marino { 1369*e4b17023SJohn Marino rtx *dest, *src; 1370*e4b17023SJohn Marino bool control_flow_insn_deleted = false; 1371*e4b17023SJohn Marino 1372*e4b17023SJohn Marino switch (GET_CODE (pat)) 1373*e4b17023SJohn Marino { 1374*e4b17023SJohn Marino case USE: 1375*e4b17023SJohn Marino /* Deaths in USE insns can happen in non optimizing compilation. 1376*e4b17023SJohn Marino Handle them by popping the dying register. */ 1377*e4b17023SJohn Marino src = get_true_reg (&XEXP (pat, 0)); 1378*e4b17023SJohn Marino if (STACK_REG_P (*src) 1379*e4b17023SJohn Marino && find_regno_note (insn, REG_DEAD, REGNO (*src))) 1380*e4b17023SJohn Marino { 1381*e4b17023SJohn Marino /* USEs are ignored for liveness information so USEs of dead 1382*e4b17023SJohn Marino register might happen. */ 1383*e4b17023SJohn Marino if (TEST_HARD_REG_BIT (regstack->reg_set, REGNO (*src))) 1384*e4b17023SJohn Marino emit_pop_insn (insn, regstack, *src, EMIT_AFTER); 1385*e4b17023SJohn Marino return control_flow_insn_deleted; 1386*e4b17023SJohn Marino } 1387*e4b17023SJohn Marino /* Uninitialized USE might happen for functions returning uninitialized 1388*e4b17023SJohn Marino value. We will properly initialize the USE on the edge to EXIT_BLOCK, 1389*e4b17023SJohn Marino so it is safe to ignore the use here. This is consistent with behavior 1390*e4b17023SJohn Marino of dataflow analyzer that ignores USE too. (This also imply that 1391*e4b17023SJohn Marino forcibly initializing the register to NaN here would lead to ICE later, 1392*e4b17023SJohn Marino since the REG_DEAD notes are not issued.) */ 1393*e4b17023SJohn Marino break; 1394*e4b17023SJohn Marino 1395*e4b17023SJohn Marino case VAR_LOCATION: 1396*e4b17023SJohn Marino gcc_unreachable (); 1397*e4b17023SJohn Marino 1398*e4b17023SJohn Marino case CLOBBER: 1399*e4b17023SJohn Marino { 1400*e4b17023SJohn Marino rtx note; 1401*e4b17023SJohn Marino 1402*e4b17023SJohn Marino dest = get_true_reg (&XEXP (pat, 0)); 1403*e4b17023SJohn Marino if (STACK_REG_P (*dest)) 1404*e4b17023SJohn Marino { 1405*e4b17023SJohn Marino note = find_reg_note (insn, REG_DEAD, *dest); 1406*e4b17023SJohn Marino 1407*e4b17023SJohn Marino if (pat != PATTERN (insn)) 1408*e4b17023SJohn Marino { 1409*e4b17023SJohn Marino /* The fix_truncdi_1 pattern wants to be able to 1410*e4b17023SJohn Marino allocate its own scratch register. It does this by 1411*e4b17023SJohn Marino clobbering an fp reg so that it is assured of an 1412*e4b17023SJohn Marino empty reg-stack register. If the register is live, 1413*e4b17023SJohn Marino kill it now. Remove the DEAD/UNUSED note so we 1414*e4b17023SJohn Marino don't try to kill it later too. 1415*e4b17023SJohn Marino 1416*e4b17023SJohn Marino In reality the UNUSED note can be absent in some 1417*e4b17023SJohn Marino complicated cases when the register is reused for 1418*e4b17023SJohn Marino partially set variable. */ 1419*e4b17023SJohn Marino 1420*e4b17023SJohn Marino if (note) 1421*e4b17023SJohn Marino emit_pop_insn (insn, regstack, *dest, EMIT_BEFORE); 1422*e4b17023SJohn Marino else 1423*e4b17023SJohn Marino note = find_reg_note (insn, REG_UNUSED, *dest); 1424*e4b17023SJohn Marino if (note) 1425*e4b17023SJohn Marino remove_note (insn, note); 1426*e4b17023SJohn Marino replace_reg (dest, FIRST_STACK_REG + 1); 1427*e4b17023SJohn Marino } 1428*e4b17023SJohn Marino else 1429*e4b17023SJohn Marino { 1430*e4b17023SJohn Marino /* A top-level clobber with no REG_DEAD, and no hard-regnum 1431*e4b17023SJohn Marino indicates an uninitialized value. Because reload removed 1432*e4b17023SJohn Marino all other clobbers, this must be due to a function 1433*e4b17023SJohn Marino returning without a value. Load up a NaN. */ 1434*e4b17023SJohn Marino 1435*e4b17023SJohn Marino if (!note) 1436*e4b17023SJohn Marino { 1437*e4b17023SJohn Marino rtx t = *dest; 1438*e4b17023SJohn Marino if (COMPLEX_MODE_P (GET_MODE (t))) 1439*e4b17023SJohn Marino { 1440*e4b17023SJohn Marino rtx u = FP_MODE_REG (REGNO (t) + 1, SFmode); 1441*e4b17023SJohn Marino if (get_hard_regnum (regstack, u) == -1) 1442*e4b17023SJohn Marino { 1443*e4b17023SJohn Marino rtx pat2 = gen_rtx_CLOBBER (VOIDmode, u); 1444*e4b17023SJohn Marino rtx insn2 = emit_insn_before (pat2, insn); 1445*e4b17023SJohn Marino control_flow_insn_deleted 1446*e4b17023SJohn Marino |= move_nan_for_stack_reg (insn2, regstack, u); 1447*e4b17023SJohn Marino } 1448*e4b17023SJohn Marino } 1449*e4b17023SJohn Marino if (get_hard_regnum (regstack, t) == -1) 1450*e4b17023SJohn Marino control_flow_insn_deleted 1451*e4b17023SJohn Marino |= move_nan_for_stack_reg (insn, regstack, t); 1452*e4b17023SJohn Marino } 1453*e4b17023SJohn Marino } 1454*e4b17023SJohn Marino } 1455*e4b17023SJohn Marino break; 1456*e4b17023SJohn Marino } 1457*e4b17023SJohn Marino 1458*e4b17023SJohn Marino case SET: 1459*e4b17023SJohn Marino { 1460*e4b17023SJohn Marino rtx *src1 = (rtx *) 0, *src2; 1461*e4b17023SJohn Marino rtx src1_note, src2_note; 1462*e4b17023SJohn Marino rtx pat_src; 1463*e4b17023SJohn Marino 1464*e4b17023SJohn Marino dest = get_true_reg (&SET_DEST (pat)); 1465*e4b17023SJohn Marino src = get_true_reg (&SET_SRC (pat)); 1466*e4b17023SJohn Marino pat_src = SET_SRC (pat); 1467*e4b17023SJohn Marino 1468*e4b17023SJohn Marino /* See if this is a `movM' pattern, and handle elsewhere if so. */ 1469*e4b17023SJohn Marino if (STACK_REG_P (*src) 1470*e4b17023SJohn Marino || (STACK_REG_P (*dest) 1471*e4b17023SJohn Marino && (REG_P (*src) || MEM_P (*src) 1472*e4b17023SJohn Marino || GET_CODE (*src) == CONST_DOUBLE))) 1473*e4b17023SJohn Marino { 1474*e4b17023SJohn Marino control_flow_insn_deleted |= move_for_stack_reg (insn, regstack, pat); 1475*e4b17023SJohn Marino break; 1476*e4b17023SJohn Marino } 1477*e4b17023SJohn Marino 1478*e4b17023SJohn Marino switch (GET_CODE (pat_src)) 1479*e4b17023SJohn Marino { 1480*e4b17023SJohn Marino case COMPARE: 1481*e4b17023SJohn Marino compare_for_stack_reg (insn, regstack, pat_src); 1482*e4b17023SJohn Marino break; 1483*e4b17023SJohn Marino 1484*e4b17023SJohn Marino case CALL: 1485*e4b17023SJohn Marino { 1486*e4b17023SJohn Marino int count; 1487*e4b17023SJohn Marino for (count = hard_regno_nregs[REGNO (*dest)][GET_MODE (*dest)]; 1488*e4b17023SJohn Marino --count >= 0;) 1489*e4b17023SJohn Marino { 1490*e4b17023SJohn Marino regstack->reg[++regstack->top] = REGNO (*dest) + count; 1491*e4b17023SJohn Marino SET_HARD_REG_BIT (regstack->reg_set, REGNO (*dest) + count); 1492*e4b17023SJohn Marino } 1493*e4b17023SJohn Marino } 1494*e4b17023SJohn Marino replace_reg (dest, FIRST_STACK_REG); 1495*e4b17023SJohn Marino break; 1496*e4b17023SJohn Marino 1497*e4b17023SJohn Marino case REG: 1498*e4b17023SJohn Marino /* This is a `tstM2' case. */ 1499*e4b17023SJohn Marino gcc_assert (*dest == cc0_rtx); 1500*e4b17023SJohn Marino src1 = src; 1501*e4b17023SJohn Marino 1502*e4b17023SJohn Marino /* Fall through. */ 1503*e4b17023SJohn Marino 1504*e4b17023SJohn Marino case FLOAT_TRUNCATE: 1505*e4b17023SJohn Marino case SQRT: 1506*e4b17023SJohn Marino case ABS: 1507*e4b17023SJohn Marino case NEG: 1508*e4b17023SJohn Marino /* These insns only operate on the top of the stack. DEST might 1509*e4b17023SJohn Marino be cc0_rtx if we're processing a tstM pattern. Also, it's 1510*e4b17023SJohn Marino possible that the tstM case results in a REG_DEAD note on the 1511*e4b17023SJohn Marino source. */ 1512*e4b17023SJohn Marino 1513*e4b17023SJohn Marino if (src1 == 0) 1514*e4b17023SJohn Marino src1 = get_true_reg (&XEXP (pat_src, 0)); 1515*e4b17023SJohn Marino 1516*e4b17023SJohn Marino emit_swap_insn (insn, regstack, *src1); 1517*e4b17023SJohn Marino 1518*e4b17023SJohn Marino src1_note = find_regno_note (insn, REG_DEAD, REGNO (*src1)); 1519*e4b17023SJohn Marino 1520*e4b17023SJohn Marino if (STACK_REG_P (*dest)) 1521*e4b17023SJohn Marino replace_reg (dest, FIRST_STACK_REG); 1522*e4b17023SJohn Marino 1523*e4b17023SJohn Marino if (src1_note) 1524*e4b17023SJohn Marino { 1525*e4b17023SJohn Marino replace_reg (&XEXP (src1_note, 0), FIRST_STACK_REG); 1526*e4b17023SJohn Marino regstack->top--; 1527*e4b17023SJohn Marino CLEAR_HARD_REG_BIT (regstack->reg_set, REGNO (*src1)); 1528*e4b17023SJohn Marino } 1529*e4b17023SJohn Marino 1530*e4b17023SJohn Marino replace_reg (src1, FIRST_STACK_REG); 1531*e4b17023SJohn Marino break; 1532*e4b17023SJohn Marino 1533*e4b17023SJohn Marino case MINUS: 1534*e4b17023SJohn Marino case DIV: 1535*e4b17023SJohn Marino /* On i386, reversed forms of subM3 and divM3 exist for 1536*e4b17023SJohn Marino MODE_FLOAT, so the same code that works for addM3 and mulM3 1537*e4b17023SJohn Marino can be used. */ 1538*e4b17023SJohn Marino case MULT: 1539*e4b17023SJohn Marino case PLUS: 1540*e4b17023SJohn Marino /* These insns can accept the top of stack as a destination 1541*e4b17023SJohn Marino from a stack reg or mem, or can use the top of stack as a 1542*e4b17023SJohn Marino source and some other stack register (possibly top of stack) 1543*e4b17023SJohn Marino as a destination. */ 1544*e4b17023SJohn Marino 1545*e4b17023SJohn Marino src1 = get_true_reg (&XEXP (pat_src, 0)); 1546*e4b17023SJohn Marino src2 = get_true_reg (&XEXP (pat_src, 1)); 1547*e4b17023SJohn Marino 1548*e4b17023SJohn Marino /* We will fix any death note later. */ 1549*e4b17023SJohn Marino 1550*e4b17023SJohn Marino if (STACK_REG_P (*src1)) 1551*e4b17023SJohn Marino src1_note = find_regno_note (insn, REG_DEAD, REGNO (*src1)); 1552*e4b17023SJohn Marino else 1553*e4b17023SJohn Marino src1_note = NULL_RTX; 1554*e4b17023SJohn Marino if (STACK_REG_P (*src2)) 1555*e4b17023SJohn Marino src2_note = find_regno_note (insn, REG_DEAD, REGNO (*src2)); 1556*e4b17023SJohn Marino else 1557*e4b17023SJohn Marino src2_note = NULL_RTX; 1558*e4b17023SJohn Marino 1559*e4b17023SJohn Marino /* If either operand is not a stack register, then the dest 1560*e4b17023SJohn Marino must be top of stack. */ 1561*e4b17023SJohn Marino 1562*e4b17023SJohn Marino if (! STACK_REG_P (*src1) || ! STACK_REG_P (*src2)) 1563*e4b17023SJohn Marino emit_swap_insn (insn, regstack, *dest); 1564*e4b17023SJohn Marino else 1565*e4b17023SJohn Marino { 1566*e4b17023SJohn Marino /* Both operands are REG. If neither operand is already 1567*e4b17023SJohn Marino at the top of stack, choose to make the one that is the 1568*e4b17023SJohn Marino dest the new top of stack. */ 1569*e4b17023SJohn Marino 1570*e4b17023SJohn Marino int src1_hard_regnum, src2_hard_regnum; 1571*e4b17023SJohn Marino 1572*e4b17023SJohn Marino src1_hard_regnum = get_hard_regnum (regstack, *src1); 1573*e4b17023SJohn Marino src2_hard_regnum = get_hard_regnum (regstack, *src2); 1574*e4b17023SJohn Marino 1575*e4b17023SJohn Marino /* If the source is not live, this is yet another case of 1576*e4b17023SJohn Marino uninitialized variables. Load up a NaN instead. */ 1577*e4b17023SJohn Marino if (src1_hard_regnum == -1) 1578*e4b17023SJohn Marino { 1579*e4b17023SJohn Marino rtx pat2 = gen_rtx_CLOBBER (VOIDmode, *src1); 1580*e4b17023SJohn Marino rtx insn2 = emit_insn_before (pat2, insn); 1581*e4b17023SJohn Marino control_flow_insn_deleted 1582*e4b17023SJohn Marino |= move_nan_for_stack_reg (insn2, regstack, *src1); 1583*e4b17023SJohn Marino } 1584*e4b17023SJohn Marino if (src2_hard_regnum == -1) 1585*e4b17023SJohn Marino { 1586*e4b17023SJohn Marino rtx pat2 = gen_rtx_CLOBBER (VOIDmode, *src2); 1587*e4b17023SJohn Marino rtx insn2 = emit_insn_before (pat2, insn); 1588*e4b17023SJohn Marino control_flow_insn_deleted 1589*e4b17023SJohn Marino |= move_nan_for_stack_reg (insn2, regstack, *src2); 1590*e4b17023SJohn Marino } 1591*e4b17023SJohn Marino 1592*e4b17023SJohn Marino if (src1_hard_regnum != FIRST_STACK_REG 1593*e4b17023SJohn Marino && src2_hard_regnum != FIRST_STACK_REG) 1594*e4b17023SJohn Marino emit_swap_insn (insn, regstack, *dest); 1595*e4b17023SJohn Marino } 1596*e4b17023SJohn Marino 1597*e4b17023SJohn Marino if (STACK_REG_P (*src1)) 1598*e4b17023SJohn Marino replace_reg (src1, get_hard_regnum (regstack, *src1)); 1599*e4b17023SJohn Marino if (STACK_REG_P (*src2)) 1600*e4b17023SJohn Marino replace_reg (src2, get_hard_regnum (regstack, *src2)); 1601*e4b17023SJohn Marino 1602*e4b17023SJohn Marino if (src1_note) 1603*e4b17023SJohn Marino { 1604*e4b17023SJohn Marino rtx src1_reg = XEXP (src1_note, 0); 1605*e4b17023SJohn Marino 1606*e4b17023SJohn Marino /* If the register that dies is at the top of stack, then 1607*e4b17023SJohn Marino the destination is somewhere else - merely substitute it. 1608*e4b17023SJohn Marino But if the reg that dies is not at top of stack, then 1609*e4b17023SJohn Marino move the top of stack to the dead reg, as though we had 1610*e4b17023SJohn Marino done the insn and then a store-with-pop. */ 1611*e4b17023SJohn Marino 1612*e4b17023SJohn Marino if (REGNO (src1_reg) == regstack->reg[regstack->top]) 1613*e4b17023SJohn Marino { 1614*e4b17023SJohn Marino SET_HARD_REG_BIT (regstack->reg_set, REGNO (*dest)); 1615*e4b17023SJohn Marino replace_reg (dest, get_hard_regnum (regstack, *dest)); 1616*e4b17023SJohn Marino } 1617*e4b17023SJohn Marino else 1618*e4b17023SJohn Marino { 1619*e4b17023SJohn Marino int regno = get_hard_regnum (regstack, src1_reg); 1620*e4b17023SJohn Marino 1621*e4b17023SJohn Marino SET_HARD_REG_BIT (regstack->reg_set, REGNO (*dest)); 1622*e4b17023SJohn Marino replace_reg (dest, regno); 1623*e4b17023SJohn Marino 1624*e4b17023SJohn Marino regstack->reg[regstack->top - (regno - FIRST_STACK_REG)] 1625*e4b17023SJohn Marino = regstack->reg[regstack->top]; 1626*e4b17023SJohn Marino } 1627*e4b17023SJohn Marino 1628*e4b17023SJohn Marino CLEAR_HARD_REG_BIT (regstack->reg_set, 1629*e4b17023SJohn Marino REGNO (XEXP (src1_note, 0))); 1630*e4b17023SJohn Marino replace_reg (&XEXP (src1_note, 0), FIRST_STACK_REG); 1631*e4b17023SJohn Marino regstack->top--; 1632*e4b17023SJohn Marino } 1633*e4b17023SJohn Marino else if (src2_note) 1634*e4b17023SJohn Marino { 1635*e4b17023SJohn Marino rtx src2_reg = XEXP (src2_note, 0); 1636*e4b17023SJohn Marino if (REGNO (src2_reg) == regstack->reg[regstack->top]) 1637*e4b17023SJohn Marino { 1638*e4b17023SJohn Marino SET_HARD_REG_BIT (regstack->reg_set, REGNO (*dest)); 1639*e4b17023SJohn Marino replace_reg (dest, get_hard_regnum (regstack, *dest)); 1640*e4b17023SJohn Marino } 1641*e4b17023SJohn Marino else 1642*e4b17023SJohn Marino { 1643*e4b17023SJohn Marino int regno = get_hard_regnum (regstack, src2_reg); 1644*e4b17023SJohn Marino 1645*e4b17023SJohn Marino SET_HARD_REG_BIT (regstack->reg_set, REGNO (*dest)); 1646*e4b17023SJohn Marino replace_reg (dest, regno); 1647*e4b17023SJohn Marino 1648*e4b17023SJohn Marino regstack->reg[regstack->top - (regno - FIRST_STACK_REG)] 1649*e4b17023SJohn Marino = regstack->reg[regstack->top]; 1650*e4b17023SJohn Marino } 1651*e4b17023SJohn Marino 1652*e4b17023SJohn Marino CLEAR_HARD_REG_BIT (regstack->reg_set, 1653*e4b17023SJohn Marino REGNO (XEXP (src2_note, 0))); 1654*e4b17023SJohn Marino replace_reg (&XEXP (src2_note, 0), FIRST_STACK_REG); 1655*e4b17023SJohn Marino regstack->top--; 1656*e4b17023SJohn Marino } 1657*e4b17023SJohn Marino else 1658*e4b17023SJohn Marino { 1659*e4b17023SJohn Marino SET_HARD_REG_BIT (regstack->reg_set, REGNO (*dest)); 1660*e4b17023SJohn Marino replace_reg (dest, get_hard_regnum (regstack, *dest)); 1661*e4b17023SJohn Marino } 1662*e4b17023SJohn Marino 1663*e4b17023SJohn Marino /* Keep operand 1 matching with destination. */ 1664*e4b17023SJohn Marino if (COMMUTATIVE_ARITH_P (pat_src) 1665*e4b17023SJohn Marino && REG_P (*src1) && REG_P (*src2) 1666*e4b17023SJohn Marino && REGNO (*src1) != REGNO (*dest)) 1667*e4b17023SJohn Marino { 1668*e4b17023SJohn Marino int tmp = REGNO (*src1); 1669*e4b17023SJohn Marino replace_reg (src1, REGNO (*src2)); 1670*e4b17023SJohn Marino replace_reg (src2, tmp); 1671*e4b17023SJohn Marino } 1672*e4b17023SJohn Marino break; 1673*e4b17023SJohn Marino 1674*e4b17023SJohn Marino case UNSPEC: 1675*e4b17023SJohn Marino switch (XINT (pat_src, 1)) 1676*e4b17023SJohn Marino { 1677*e4b17023SJohn Marino case UNSPEC_STA: 1678*e4b17023SJohn Marino case UNSPEC_FIST: 1679*e4b17023SJohn Marino 1680*e4b17023SJohn Marino case UNSPEC_FIST_FLOOR: 1681*e4b17023SJohn Marino case UNSPEC_FIST_CEIL: 1682*e4b17023SJohn Marino 1683*e4b17023SJohn Marino /* These insns only operate on the top of the stack. */ 1684*e4b17023SJohn Marino 1685*e4b17023SJohn Marino src1 = get_true_reg (&XVECEXP (pat_src, 0, 0)); 1686*e4b17023SJohn Marino emit_swap_insn (insn, regstack, *src1); 1687*e4b17023SJohn Marino 1688*e4b17023SJohn Marino src1_note = find_regno_note (insn, REG_DEAD, REGNO (*src1)); 1689*e4b17023SJohn Marino 1690*e4b17023SJohn Marino if (STACK_REG_P (*dest)) 1691*e4b17023SJohn Marino replace_reg (dest, FIRST_STACK_REG); 1692*e4b17023SJohn Marino 1693*e4b17023SJohn Marino if (src1_note) 1694*e4b17023SJohn Marino { 1695*e4b17023SJohn Marino replace_reg (&XEXP (src1_note, 0), FIRST_STACK_REG); 1696*e4b17023SJohn Marino regstack->top--; 1697*e4b17023SJohn Marino CLEAR_HARD_REG_BIT (regstack->reg_set, REGNO (*src1)); 1698*e4b17023SJohn Marino } 1699*e4b17023SJohn Marino 1700*e4b17023SJohn Marino replace_reg (src1, FIRST_STACK_REG); 1701*e4b17023SJohn Marino break; 1702*e4b17023SJohn Marino 1703*e4b17023SJohn Marino case UNSPEC_FXAM: 1704*e4b17023SJohn Marino 1705*e4b17023SJohn Marino /* This insn only operate on the top of the stack. */ 1706*e4b17023SJohn Marino 1707*e4b17023SJohn Marino src1 = get_true_reg (&XVECEXP (pat_src, 0, 0)); 1708*e4b17023SJohn Marino emit_swap_insn (insn, regstack, *src1); 1709*e4b17023SJohn Marino 1710*e4b17023SJohn Marino src1_note = find_regno_note (insn, REG_DEAD, REGNO (*src1)); 1711*e4b17023SJohn Marino 1712*e4b17023SJohn Marino replace_reg (src1, FIRST_STACK_REG); 1713*e4b17023SJohn Marino 1714*e4b17023SJohn Marino if (src1_note) 1715*e4b17023SJohn Marino { 1716*e4b17023SJohn Marino remove_regno_note (insn, REG_DEAD, 1717*e4b17023SJohn Marino REGNO (XEXP (src1_note, 0))); 1718*e4b17023SJohn Marino emit_pop_insn (insn, regstack, XEXP (src1_note, 0), 1719*e4b17023SJohn Marino EMIT_AFTER); 1720*e4b17023SJohn Marino } 1721*e4b17023SJohn Marino 1722*e4b17023SJohn Marino break; 1723*e4b17023SJohn Marino 1724*e4b17023SJohn Marino case UNSPEC_SIN: 1725*e4b17023SJohn Marino case UNSPEC_COS: 1726*e4b17023SJohn Marino case UNSPEC_FRNDINT: 1727*e4b17023SJohn Marino case UNSPEC_F2XM1: 1728*e4b17023SJohn Marino 1729*e4b17023SJohn Marino case UNSPEC_FRNDINT_FLOOR: 1730*e4b17023SJohn Marino case UNSPEC_FRNDINT_CEIL: 1731*e4b17023SJohn Marino case UNSPEC_FRNDINT_TRUNC: 1732*e4b17023SJohn Marino case UNSPEC_FRNDINT_MASK_PM: 1733*e4b17023SJohn Marino 1734*e4b17023SJohn Marino /* Above insns operate on the top of the stack. */ 1735*e4b17023SJohn Marino 1736*e4b17023SJohn Marino case UNSPEC_SINCOS_COS: 1737*e4b17023SJohn Marino case UNSPEC_XTRACT_FRACT: 1738*e4b17023SJohn Marino 1739*e4b17023SJohn Marino /* Above insns operate on the top two stack slots, 1740*e4b17023SJohn Marino first part of one input, double output insn. */ 1741*e4b17023SJohn Marino 1742*e4b17023SJohn Marino src1 = get_true_reg (&XVECEXP (pat_src, 0, 0)); 1743*e4b17023SJohn Marino 1744*e4b17023SJohn Marino emit_swap_insn (insn, regstack, *src1); 1745*e4b17023SJohn Marino 1746*e4b17023SJohn Marino /* Input should never die, it is replaced with output. */ 1747*e4b17023SJohn Marino src1_note = find_regno_note (insn, REG_DEAD, REGNO (*src1)); 1748*e4b17023SJohn Marino gcc_assert (!src1_note); 1749*e4b17023SJohn Marino 1750*e4b17023SJohn Marino if (STACK_REG_P (*dest)) 1751*e4b17023SJohn Marino replace_reg (dest, FIRST_STACK_REG); 1752*e4b17023SJohn Marino 1753*e4b17023SJohn Marino replace_reg (src1, FIRST_STACK_REG); 1754*e4b17023SJohn Marino break; 1755*e4b17023SJohn Marino 1756*e4b17023SJohn Marino case UNSPEC_SINCOS_SIN: 1757*e4b17023SJohn Marino case UNSPEC_XTRACT_EXP: 1758*e4b17023SJohn Marino 1759*e4b17023SJohn Marino /* These insns operate on the top two stack slots, 1760*e4b17023SJohn Marino second part of one input, double output insn. */ 1761*e4b17023SJohn Marino 1762*e4b17023SJohn Marino regstack->top++; 1763*e4b17023SJohn Marino /* FALLTHRU */ 1764*e4b17023SJohn Marino 1765*e4b17023SJohn Marino case UNSPEC_TAN: 1766*e4b17023SJohn Marino 1767*e4b17023SJohn Marino /* For UNSPEC_TAN, regstack->top is already increased 1768*e4b17023SJohn Marino by inherent load of constant 1.0. */ 1769*e4b17023SJohn Marino 1770*e4b17023SJohn Marino /* Output value is generated in the second stack slot. 1771*e4b17023SJohn Marino Move current value from second slot to the top. */ 1772*e4b17023SJohn Marino regstack->reg[regstack->top] 1773*e4b17023SJohn Marino = regstack->reg[regstack->top - 1]; 1774*e4b17023SJohn Marino 1775*e4b17023SJohn Marino gcc_assert (STACK_REG_P (*dest)); 1776*e4b17023SJohn Marino 1777*e4b17023SJohn Marino regstack->reg[regstack->top - 1] = REGNO (*dest); 1778*e4b17023SJohn Marino SET_HARD_REG_BIT (regstack->reg_set, REGNO (*dest)); 1779*e4b17023SJohn Marino replace_reg (dest, FIRST_STACK_REG + 1); 1780*e4b17023SJohn Marino 1781*e4b17023SJohn Marino src1 = get_true_reg (&XVECEXP (pat_src, 0, 0)); 1782*e4b17023SJohn Marino 1783*e4b17023SJohn Marino replace_reg (src1, FIRST_STACK_REG); 1784*e4b17023SJohn Marino break; 1785*e4b17023SJohn Marino 1786*e4b17023SJohn Marino case UNSPEC_FPATAN: 1787*e4b17023SJohn Marino case UNSPEC_FYL2X: 1788*e4b17023SJohn Marino case UNSPEC_FYL2XP1: 1789*e4b17023SJohn Marino /* These insns operate on the top two stack slots. */ 1790*e4b17023SJohn Marino 1791*e4b17023SJohn Marino src1 = get_true_reg (&XVECEXP (pat_src, 0, 0)); 1792*e4b17023SJohn Marino src2 = get_true_reg (&XVECEXP (pat_src, 0, 1)); 1793*e4b17023SJohn Marino 1794*e4b17023SJohn Marino src1_note = find_regno_note (insn, REG_DEAD, REGNO (*src1)); 1795*e4b17023SJohn Marino src2_note = find_regno_note (insn, REG_DEAD, REGNO (*src2)); 1796*e4b17023SJohn Marino 1797*e4b17023SJohn Marino swap_to_top (insn, regstack, *src1, *src2); 1798*e4b17023SJohn Marino 1799*e4b17023SJohn Marino replace_reg (src1, FIRST_STACK_REG); 1800*e4b17023SJohn Marino replace_reg (src2, FIRST_STACK_REG + 1); 1801*e4b17023SJohn Marino 1802*e4b17023SJohn Marino if (src1_note) 1803*e4b17023SJohn Marino replace_reg (&XEXP (src1_note, 0), FIRST_STACK_REG); 1804*e4b17023SJohn Marino if (src2_note) 1805*e4b17023SJohn Marino replace_reg (&XEXP (src2_note, 0), FIRST_STACK_REG + 1); 1806*e4b17023SJohn Marino 1807*e4b17023SJohn Marino /* Pop both input operands from the stack. */ 1808*e4b17023SJohn Marino CLEAR_HARD_REG_BIT (regstack->reg_set, 1809*e4b17023SJohn Marino regstack->reg[regstack->top]); 1810*e4b17023SJohn Marino CLEAR_HARD_REG_BIT (regstack->reg_set, 1811*e4b17023SJohn Marino regstack->reg[regstack->top - 1]); 1812*e4b17023SJohn Marino regstack->top -= 2; 1813*e4b17023SJohn Marino 1814*e4b17023SJohn Marino /* Push the result back onto the stack. */ 1815*e4b17023SJohn Marino regstack->reg[++regstack->top] = REGNO (*dest); 1816*e4b17023SJohn Marino SET_HARD_REG_BIT (regstack->reg_set, REGNO (*dest)); 1817*e4b17023SJohn Marino replace_reg (dest, FIRST_STACK_REG); 1818*e4b17023SJohn Marino break; 1819*e4b17023SJohn Marino 1820*e4b17023SJohn Marino case UNSPEC_FSCALE_FRACT: 1821*e4b17023SJohn Marino case UNSPEC_FPREM_F: 1822*e4b17023SJohn Marino case UNSPEC_FPREM1_F: 1823*e4b17023SJohn Marino /* These insns operate on the top two stack slots, 1824*e4b17023SJohn Marino first part of double input, double output insn. */ 1825*e4b17023SJohn Marino 1826*e4b17023SJohn Marino src1 = get_true_reg (&XVECEXP (pat_src, 0, 0)); 1827*e4b17023SJohn Marino src2 = get_true_reg (&XVECEXP (pat_src, 0, 1)); 1828*e4b17023SJohn Marino 1829*e4b17023SJohn Marino src1_note = find_regno_note (insn, REG_DEAD, REGNO (*src1)); 1830*e4b17023SJohn Marino src2_note = find_regno_note (insn, REG_DEAD, REGNO (*src2)); 1831*e4b17023SJohn Marino 1832*e4b17023SJohn Marino /* Inputs should never die, they are 1833*e4b17023SJohn Marino replaced with outputs. */ 1834*e4b17023SJohn Marino gcc_assert (!src1_note); 1835*e4b17023SJohn Marino gcc_assert (!src2_note); 1836*e4b17023SJohn Marino 1837*e4b17023SJohn Marino swap_to_top (insn, regstack, *src1, *src2); 1838*e4b17023SJohn Marino 1839*e4b17023SJohn Marino /* Push the result back onto stack. Empty stack slot 1840*e4b17023SJohn Marino will be filled in second part of insn. */ 1841*e4b17023SJohn Marino if (STACK_REG_P (*dest)) 1842*e4b17023SJohn Marino { 1843*e4b17023SJohn Marino regstack->reg[regstack->top] = REGNO (*dest); 1844*e4b17023SJohn Marino SET_HARD_REG_BIT (regstack->reg_set, REGNO (*dest)); 1845*e4b17023SJohn Marino replace_reg (dest, FIRST_STACK_REG); 1846*e4b17023SJohn Marino } 1847*e4b17023SJohn Marino 1848*e4b17023SJohn Marino replace_reg (src1, FIRST_STACK_REG); 1849*e4b17023SJohn Marino replace_reg (src2, FIRST_STACK_REG + 1); 1850*e4b17023SJohn Marino break; 1851*e4b17023SJohn Marino 1852*e4b17023SJohn Marino case UNSPEC_FSCALE_EXP: 1853*e4b17023SJohn Marino case UNSPEC_FPREM_U: 1854*e4b17023SJohn Marino case UNSPEC_FPREM1_U: 1855*e4b17023SJohn Marino /* These insns operate on the top two stack slots, 1856*e4b17023SJohn Marino second part of double input, double output insn. */ 1857*e4b17023SJohn Marino 1858*e4b17023SJohn Marino src1 = get_true_reg (&XVECEXP (pat_src, 0, 0)); 1859*e4b17023SJohn Marino src2 = get_true_reg (&XVECEXP (pat_src, 0, 1)); 1860*e4b17023SJohn Marino 1861*e4b17023SJohn Marino /* Push the result back onto stack. Fill empty slot from 1862*e4b17023SJohn Marino first part of insn and fix top of stack pointer. */ 1863*e4b17023SJohn Marino if (STACK_REG_P (*dest)) 1864*e4b17023SJohn Marino { 1865*e4b17023SJohn Marino regstack->reg[regstack->top - 1] = REGNO (*dest); 1866*e4b17023SJohn Marino SET_HARD_REG_BIT (regstack->reg_set, REGNO (*dest)); 1867*e4b17023SJohn Marino replace_reg (dest, FIRST_STACK_REG + 1); 1868*e4b17023SJohn Marino } 1869*e4b17023SJohn Marino 1870*e4b17023SJohn Marino replace_reg (src1, FIRST_STACK_REG); 1871*e4b17023SJohn Marino replace_reg (src2, FIRST_STACK_REG + 1); 1872*e4b17023SJohn Marino break; 1873*e4b17023SJohn Marino 1874*e4b17023SJohn Marino case UNSPEC_C2_FLAG: 1875*e4b17023SJohn Marino /* This insn operates on the top two stack slots, 1876*e4b17023SJohn Marino third part of C2 setting double input insn. */ 1877*e4b17023SJohn Marino 1878*e4b17023SJohn Marino src1 = get_true_reg (&XVECEXP (pat_src, 0, 0)); 1879*e4b17023SJohn Marino src2 = get_true_reg (&XVECEXP (pat_src, 0, 1)); 1880*e4b17023SJohn Marino 1881*e4b17023SJohn Marino replace_reg (src1, FIRST_STACK_REG); 1882*e4b17023SJohn Marino replace_reg (src2, FIRST_STACK_REG + 1); 1883*e4b17023SJohn Marino break; 1884*e4b17023SJohn Marino 1885*e4b17023SJohn Marino case UNSPEC_SAHF: 1886*e4b17023SJohn Marino /* (unspec [(unspec [(compare)] UNSPEC_FNSTSW)] UNSPEC_SAHF) 1887*e4b17023SJohn Marino The combination matches the PPRO fcomi instruction. */ 1888*e4b17023SJohn Marino 1889*e4b17023SJohn Marino pat_src = XVECEXP (pat_src, 0, 0); 1890*e4b17023SJohn Marino gcc_assert (GET_CODE (pat_src) == UNSPEC); 1891*e4b17023SJohn Marino gcc_assert (XINT (pat_src, 1) == UNSPEC_FNSTSW); 1892*e4b17023SJohn Marino /* Fall through. */ 1893*e4b17023SJohn Marino 1894*e4b17023SJohn Marino case UNSPEC_FNSTSW: 1895*e4b17023SJohn Marino /* Combined fcomp+fnstsw generated for doing well with 1896*e4b17023SJohn Marino CSE. When optimizing this would have been broken 1897*e4b17023SJohn Marino up before now. */ 1898*e4b17023SJohn Marino 1899*e4b17023SJohn Marino pat_src = XVECEXP (pat_src, 0, 0); 1900*e4b17023SJohn Marino gcc_assert (GET_CODE (pat_src) == COMPARE); 1901*e4b17023SJohn Marino 1902*e4b17023SJohn Marino compare_for_stack_reg (insn, regstack, pat_src); 1903*e4b17023SJohn Marino break; 1904*e4b17023SJohn Marino 1905*e4b17023SJohn Marino default: 1906*e4b17023SJohn Marino gcc_unreachable (); 1907*e4b17023SJohn Marino } 1908*e4b17023SJohn Marino break; 1909*e4b17023SJohn Marino 1910*e4b17023SJohn Marino case IF_THEN_ELSE: 1911*e4b17023SJohn Marino /* This insn requires the top of stack to be the destination. */ 1912*e4b17023SJohn Marino 1913*e4b17023SJohn Marino src1 = get_true_reg (&XEXP (pat_src, 1)); 1914*e4b17023SJohn Marino src2 = get_true_reg (&XEXP (pat_src, 2)); 1915*e4b17023SJohn Marino 1916*e4b17023SJohn Marino src1_note = find_regno_note (insn, REG_DEAD, REGNO (*src1)); 1917*e4b17023SJohn Marino src2_note = find_regno_note (insn, REG_DEAD, REGNO (*src2)); 1918*e4b17023SJohn Marino 1919*e4b17023SJohn Marino /* If the comparison operator is an FP comparison operator, 1920*e4b17023SJohn Marino it is handled correctly by compare_for_stack_reg () who 1921*e4b17023SJohn Marino will move the destination to the top of stack. But if the 1922*e4b17023SJohn Marino comparison operator is not an FP comparison operator, we 1923*e4b17023SJohn Marino have to handle it here. */ 1924*e4b17023SJohn Marino if (get_hard_regnum (regstack, *dest) >= FIRST_STACK_REG 1925*e4b17023SJohn Marino && REGNO (*dest) != regstack->reg[regstack->top]) 1926*e4b17023SJohn Marino { 1927*e4b17023SJohn Marino /* In case one of operands is the top of stack and the operands 1928*e4b17023SJohn Marino dies, it is safe to make it the destination operand by 1929*e4b17023SJohn Marino reversing the direction of cmove and avoid fxch. */ 1930*e4b17023SJohn Marino if ((REGNO (*src1) == regstack->reg[regstack->top] 1931*e4b17023SJohn Marino && src1_note) 1932*e4b17023SJohn Marino || (REGNO (*src2) == regstack->reg[regstack->top] 1933*e4b17023SJohn Marino && src2_note)) 1934*e4b17023SJohn Marino { 1935*e4b17023SJohn Marino int idx1 = (get_hard_regnum (regstack, *src1) 1936*e4b17023SJohn Marino - FIRST_STACK_REG); 1937*e4b17023SJohn Marino int idx2 = (get_hard_regnum (regstack, *src2) 1938*e4b17023SJohn Marino - FIRST_STACK_REG); 1939*e4b17023SJohn Marino 1940*e4b17023SJohn Marino /* Make reg-stack believe that the operands are already 1941*e4b17023SJohn Marino swapped on the stack */ 1942*e4b17023SJohn Marino regstack->reg[regstack->top - idx1] = REGNO (*src2); 1943*e4b17023SJohn Marino regstack->reg[regstack->top - idx2] = REGNO (*src1); 1944*e4b17023SJohn Marino 1945*e4b17023SJohn Marino /* Reverse condition to compensate the operand swap. 1946*e4b17023SJohn Marino i386 do have comparison always reversible. */ 1947*e4b17023SJohn Marino PUT_CODE (XEXP (pat_src, 0), 1948*e4b17023SJohn Marino reversed_comparison_code (XEXP (pat_src, 0), insn)); 1949*e4b17023SJohn Marino } 1950*e4b17023SJohn Marino else 1951*e4b17023SJohn Marino emit_swap_insn (insn, regstack, *dest); 1952*e4b17023SJohn Marino } 1953*e4b17023SJohn Marino 1954*e4b17023SJohn Marino { 1955*e4b17023SJohn Marino rtx src_note [3]; 1956*e4b17023SJohn Marino int i; 1957*e4b17023SJohn Marino 1958*e4b17023SJohn Marino src_note[0] = 0; 1959*e4b17023SJohn Marino src_note[1] = src1_note; 1960*e4b17023SJohn Marino src_note[2] = src2_note; 1961*e4b17023SJohn Marino 1962*e4b17023SJohn Marino if (STACK_REG_P (*src1)) 1963*e4b17023SJohn Marino replace_reg (src1, get_hard_regnum (regstack, *src1)); 1964*e4b17023SJohn Marino if (STACK_REG_P (*src2)) 1965*e4b17023SJohn Marino replace_reg (src2, get_hard_regnum (regstack, *src2)); 1966*e4b17023SJohn Marino 1967*e4b17023SJohn Marino for (i = 1; i <= 2; i++) 1968*e4b17023SJohn Marino if (src_note [i]) 1969*e4b17023SJohn Marino { 1970*e4b17023SJohn Marino int regno = REGNO (XEXP (src_note[i], 0)); 1971*e4b17023SJohn Marino 1972*e4b17023SJohn Marino /* If the register that dies is not at the top of 1973*e4b17023SJohn Marino stack, then move the top of stack to the dead reg. 1974*e4b17023SJohn Marino Top of stack should never die, as it is the 1975*e4b17023SJohn Marino destination. */ 1976*e4b17023SJohn Marino gcc_assert (regno != regstack->reg[regstack->top]); 1977*e4b17023SJohn Marino remove_regno_note (insn, REG_DEAD, regno); 1978*e4b17023SJohn Marino emit_pop_insn (insn, regstack, XEXP (src_note[i], 0), 1979*e4b17023SJohn Marino EMIT_AFTER); 1980*e4b17023SJohn Marino } 1981*e4b17023SJohn Marino } 1982*e4b17023SJohn Marino 1983*e4b17023SJohn Marino /* Make dest the top of stack. Add dest to regstack if 1984*e4b17023SJohn Marino not present. */ 1985*e4b17023SJohn Marino if (get_hard_regnum (regstack, *dest) < FIRST_STACK_REG) 1986*e4b17023SJohn Marino regstack->reg[++regstack->top] = REGNO (*dest); 1987*e4b17023SJohn Marino SET_HARD_REG_BIT (regstack->reg_set, REGNO (*dest)); 1988*e4b17023SJohn Marino replace_reg (dest, FIRST_STACK_REG); 1989*e4b17023SJohn Marino break; 1990*e4b17023SJohn Marino 1991*e4b17023SJohn Marino default: 1992*e4b17023SJohn Marino gcc_unreachable (); 1993*e4b17023SJohn Marino } 1994*e4b17023SJohn Marino break; 1995*e4b17023SJohn Marino } 1996*e4b17023SJohn Marino 1997*e4b17023SJohn Marino default: 1998*e4b17023SJohn Marino break; 1999*e4b17023SJohn Marino } 2000*e4b17023SJohn Marino 2001*e4b17023SJohn Marino return control_flow_insn_deleted; 2002*e4b17023SJohn Marino } 2003*e4b17023SJohn Marino 2004*e4b17023SJohn Marino /* Substitute hard regnums for any stack regs in INSN, which has 2005*e4b17023SJohn Marino N_INPUTS inputs and N_OUTPUTS outputs. REGSTACK is the stack info 2006*e4b17023SJohn Marino before the insn, and is updated with changes made here. 2007*e4b17023SJohn Marino 2008*e4b17023SJohn Marino There are several requirements and assumptions about the use of 2009*e4b17023SJohn Marino stack-like regs in asm statements. These rules are enforced by 2010*e4b17023SJohn Marino record_asm_stack_regs; see comments there for details. Any 2011*e4b17023SJohn Marino asm_operands left in the RTL at this point may be assume to meet the 2012*e4b17023SJohn Marino requirements, since record_asm_stack_regs removes any problem asm. */ 2013*e4b17023SJohn Marino 2014*e4b17023SJohn Marino static void 2015*e4b17023SJohn Marino subst_asm_stack_regs (rtx insn, stack regstack) 2016*e4b17023SJohn Marino { 2017*e4b17023SJohn Marino rtx body = PATTERN (insn); 2018*e4b17023SJohn Marino int alt; 2019*e4b17023SJohn Marino 2020*e4b17023SJohn Marino rtx *note_reg; /* Array of note contents */ 2021*e4b17023SJohn Marino rtx **note_loc; /* Address of REG field of each note */ 2022*e4b17023SJohn Marino enum reg_note *note_kind; /* The type of each note */ 2023*e4b17023SJohn Marino 2024*e4b17023SJohn Marino rtx *clobber_reg = 0; 2025*e4b17023SJohn Marino rtx **clobber_loc = 0; 2026*e4b17023SJohn Marino 2027*e4b17023SJohn Marino struct stack_def temp_stack; 2028*e4b17023SJohn Marino int n_notes; 2029*e4b17023SJohn Marino int n_clobbers; 2030*e4b17023SJohn Marino rtx note; 2031*e4b17023SJohn Marino int i; 2032*e4b17023SJohn Marino int n_inputs, n_outputs; 2033*e4b17023SJohn Marino 2034*e4b17023SJohn Marino if (! check_asm_stack_operands (insn)) 2035*e4b17023SJohn Marino return; 2036*e4b17023SJohn Marino 2037*e4b17023SJohn Marino /* Find out what the constraints required. If no constraint 2038*e4b17023SJohn Marino alternative matches, that is a compiler bug: we should have caught 2039*e4b17023SJohn Marino such an insn in check_asm_stack_operands. */ 2040*e4b17023SJohn Marino extract_insn (insn); 2041*e4b17023SJohn Marino constrain_operands (1); 2042*e4b17023SJohn Marino alt = which_alternative; 2043*e4b17023SJohn Marino 2044*e4b17023SJohn Marino preprocess_constraints (); 2045*e4b17023SJohn Marino 2046*e4b17023SJohn Marino get_asm_operands_in_out (body, &n_outputs, &n_inputs); 2047*e4b17023SJohn Marino 2048*e4b17023SJohn Marino gcc_assert (alt >= 0); 2049*e4b17023SJohn Marino 2050*e4b17023SJohn Marino /* Strip SUBREGs here to make the following code simpler. */ 2051*e4b17023SJohn Marino for (i = 0; i < recog_data.n_operands; i++) 2052*e4b17023SJohn Marino if (GET_CODE (recog_data.operand[i]) == SUBREG 2053*e4b17023SJohn Marino && REG_P (SUBREG_REG (recog_data.operand[i]))) 2054*e4b17023SJohn Marino { 2055*e4b17023SJohn Marino recog_data.operand_loc[i] = & SUBREG_REG (recog_data.operand[i]); 2056*e4b17023SJohn Marino recog_data.operand[i] = SUBREG_REG (recog_data.operand[i]); 2057*e4b17023SJohn Marino } 2058*e4b17023SJohn Marino 2059*e4b17023SJohn Marino /* Set up NOTE_REG, NOTE_LOC and NOTE_KIND. */ 2060*e4b17023SJohn Marino 2061*e4b17023SJohn Marino for (i = 0, note = REG_NOTES (insn); note; note = XEXP (note, 1)) 2062*e4b17023SJohn Marino i++; 2063*e4b17023SJohn Marino 2064*e4b17023SJohn Marino note_reg = XALLOCAVEC (rtx, i); 2065*e4b17023SJohn Marino note_loc = XALLOCAVEC (rtx *, i); 2066*e4b17023SJohn Marino note_kind = XALLOCAVEC (enum reg_note, i); 2067*e4b17023SJohn Marino 2068*e4b17023SJohn Marino n_notes = 0; 2069*e4b17023SJohn Marino for (note = REG_NOTES (insn); note; note = XEXP (note, 1)) 2070*e4b17023SJohn Marino { 2071*e4b17023SJohn Marino rtx reg = XEXP (note, 0); 2072*e4b17023SJohn Marino rtx *loc = & XEXP (note, 0); 2073*e4b17023SJohn Marino 2074*e4b17023SJohn Marino if (GET_CODE (reg) == SUBREG && REG_P (SUBREG_REG (reg))) 2075*e4b17023SJohn Marino { 2076*e4b17023SJohn Marino loc = & SUBREG_REG (reg); 2077*e4b17023SJohn Marino reg = SUBREG_REG (reg); 2078*e4b17023SJohn Marino } 2079*e4b17023SJohn Marino 2080*e4b17023SJohn Marino if (STACK_REG_P (reg) 2081*e4b17023SJohn Marino && (REG_NOTE_KIND (note) == REG_DEAD 2082*e4b17023SJohn Marino || REG_NOTE_KIND (note) == REG_UNUSED)) 2083*e4b17023SJohn Marino { 2084*e4b17023SJohn Marino note_reg[n_notes] = reg; 2085*e4b17023SJohn Marino note_loc[n_notes] = loc; 2086*e4b17023SJohn Marino note_kind[n_notes] = REG_NOTE_KIND (note); 2087*e4b17023SJohn Marino n_notes++; 2088*e4b17023SJohn Marino } 2089*e4b17023SJohn Marino } 2090*e4b17023SJohn Marino 2091*e4b17023SJohn Marino /* Set up CLOBBER_REG and CLOBBER_LOC. */ 2092*e4b17023SJohn Marino 2093*e4b17023SJohn Marino n_clobbers = 0; 2094*e4b17023SJohn Marino 2095*e4b17023SJohn Marino if (GET_CODE (body) == PARALLEL) 2096*e4b17023SJohn Marino { 2097*e4b17023SJohn Marino clobber_reg = XALLOCAVEC (rtx, XVECLEN (body, 0)); 2098*e4b17023SJohn Marino clobber_loc = XALLOCAVEC (rtx *, XVECLEN (body, 0)); 2099*e4b17023SJohn Marino 2100*e4b17023SJohn Marino for (i = 0; i < XVECLEN (body, 0); i++) 2101*e4b17023SJohn Marino if (GET_CODE (XVECEXP (body, 0, i)) == CLOBBER) 2102*e4b17023SJohn Marino { 2103*e4b17023SJohn Marino rtx clobber = XVECEXP (body, 0, i); 2104*e4b17023SJohn Marino rtx reg = XEXP (clobber, 0); 2105*e4b17023SJohn Marino rtx *loc = & XEXP (clobber, 0); 2106*e4b17023SJohn Marino 2107*e4b17023SJohn Marino if (GET_CODE (reg) == SUBREG && REG_P (SUBREG_REG (reg))) 2108*e4b17023SJohn Marino { 2109*e4b17023SJohn Marino loc = & SUBREG_REG (reg); 2110*e4b17023SJohn Marino reg = SUBREG_REG (reg); 2111*e4b17023SJohn Marino } 2112*e4b17023SJohn Marino 2113*e4b17023SJohn Marino if (STACK_REG_P (reg)) 2114*e4b17023SJohn Marino { 2115*e4b17023SJohn Marino clobber_reg[n_clobbers] = reg; 2116*e4b17023SJohn Marino clobber_loc[n_clobbers] = loc; 2117*e4b17023SJohn Marino n_clobbers++; 2118*e4b17023SJohn Marino } 2119*e4b17023SJohn Marino } 2120*e4b17023SJohn Marino } 2121*e4b17023SJohn Marino 2122*e4b17023SJohn Marino temp_stack = *regstack; 2123*e4b17023SJohn Marino 2124*e4b17023SJohn Marino /* Put the input regs into the desired place in TEMP_STACK. */ 2125*e4b17023SJohn Marino 2126*e4b17023SJohn Marino for (i = n_outputs; i < n_outputs + n_inputs; i++) 2127*e4b17023SJohn Marino if (STACK_REG_P (recog_data.operand[i]) 2128*e4b17023SJohn Marino && reg_class_subset_p (recog_op_alt[i][alt].cl, 2129*e4b17023SJohn Marino FLOAT_REGS) 2130*e4b17023SJohn Marino && recog_op_alt[i][alt].cl != FLOAT_REGS) 2131*e4b17023SJohn Marino { 2132*e4b17023SJohn Marino /* If an operand needs to be in a particular reg in 2133*e4b17023SJohn Marino FLOAT_REGS, the constraint was either 't' or 'u'. Since 2134*e4b17023SJohn Marino these constraints are for single register classes, and 2135*e4b17023SJohn Marino reload guaranteed that operand[i] is already in that class, 2136*e4b17023SJohn Marino we can just use REGNO (recog_data.operand[i]) to know which 2137*e4b17023SJohn Marino actual reg this operand needs to be in. */ 2138*e4b17023SJohn Marino 2139*e4b17023SJohn Marino int regno = get_hard_regnum (&temp_stack, recog_data.operand[i]); 2140*e4b17023SJohn Marino 2141*e4b17023SJohn Marino gcc_assert (regno >= 0); 2142*e4b17023SJohn Marino 2143*e4b17023SJohn Marino if ((unsigned int) regno != REGNO (recog_data.operand[i])) 2144*e4b17023SJohn Marino { 2145*e4b17023SJohn Marino /* recog_data.operand[i] is not in the right place. Find 2146*e4b17023SJohn Marino it and swap it with whatever is already in I's place. 2147*e4b17023SJohn Marino K is where recog_data.operand[i] is now. J is where it 2148*e4b17023SJohn Marino should be. */ 2149*e4b17023SJohn Marino int j, k, temp; 2150*e4b17023SJohn Marino 2151*e4b17023SJohn Marino k = temp_stack.top - (regno - FIRST_STACK_REG); 2152*e4b17023SJohn Marino j = (temp_stack.top 2153*e4b17023SJohn Marino - (REGNO (recog_data.operand[i]) - FIRST_STACK_REG)); 2154*e4b17023SJohn Marino 2155*e4b17023SJohn Marino temp = temp_stack.reg[k]; 2156*e4b17023SJohn Marino temp_stack.reg[k] = temp_stack.reg[j]; 2157*e4b17023SJohn Marino temp_stack.reg[j] = temp; 2158*e4b17023SJohn Marino } 2159*e4b17023SJohn Marino } 2160*e4b17023SJohn Marino 2161*e4b17023SJohn Marino /* Emit insns before INSN to make sure the reg-stack is in the right 2162*e4b17023SJohn Marino order. */ 2163*e4b17023SJohn Marino 2164*e4b17023SJohn Marino change_stack (insn, regstack, &temp_stack, EMIT_BEFORE); 2165*e4b17023SJohn Marino 2166*e4b17023SJohn Marino /* Make the needed input register substitutions. Do death notes and 2167*e4b17023SJohn Marino clobbers too, because these are for inputs, not outputs. */ 2168*e4b17023SJohn Marino 2169*e4b17023SJohn Marino for (i = n_outputs; i < n_outputs + n_inputs; i++) 2170*e4b17023SJohn Marino if (STACK_REG_P (recog_data.operand[i])) 2171*e4b17023SJohn Marino { 2172*e4b17023SJohn Marino int regnum = get_hard_regnum (regstack, recog_data.operand[i]); 2173*e4b17023SJohn Marino 2174*e4b17023SJohn Marino gcc_assert (regnum >= 0); 2175*e4b17023SJohn Marino 2176*e4b17023SJohn Marino replace_reg (recog_data.operand_loc[i], regnum); 2177*e4b17023SJohn Marino } 2178*e4b17023SJohn Marino 2179*e4b17023SJohn Marino for (i = 0; i < n_notes; i++) 2180*e4b17023SJohn Marino if (note_kind[i] == REG_DEAD) 2181*e4b17023SJohn Marino { 2182*e4b17023SJohn Marino int regnum = get_hard_regnum (regstack, note_reg[i]); 2183*e4b17023SJohn Marino 2184*e4b17023SJohn Marino gcc_assert (regnum >= 0); 2185*e4b17023SJohn Marino 2186*e4b17023SJohn Marino replace_reg (note_loc[i], regnum); 2187*e4b17023SJohn Marino } 2188*e4b17023SJohn Marino 2189*e4b17023SJohn Marino for (i = 0; i < n_clobbers; i++) 2190*e4b17023SJohn Marino { 2191*e4b17023SJohn Marino /* It's OK for a CLOBBER to reference a reg that is not live. 2192*e4b17023SJohn Marino Don't try to replace it in that case. */ 2193*e4b17023SJohn Marino int regnum = get_hard_regnum (regstack, clobber_reg[i]); 2194*e4b17023SJohn Marino 2195*e4b17023SJohn Marino if (regnum >= 0) 2196*e4b17023SJohn Marino { 2197*e4b17023SJohn Marino /* Sigh - clobbers always have QImode. But replace_reg knows 2198*e4b17023SJohn Marino that these regs can't be MODE_INT and will assert. Just put 2199*e4b17023SJohn Marino the right reg there without calling replace_reg. */ 2200*e4b17023SJohn Marino 2201*e4b17023SJohn Marino *clobber_loc[i] = FP_MODE_REG (regnum, DFmode); 2202*e4b17023SJohn Marino } 2203*e4b17023SJohn Marino } 2204*e4b17023SJohn Marino 2205*e4b17023SJohn Marino /* Now remove from REGSTACK any inputs that the asm implicitly popped. */ 2206*e4b17023SJohn Marino 2207*e4b17023SJohn Marino for (i = n_outputs; i < n_outputs + n_inputs; i++) 2208*e4b17023SJohn Marino if (STACK_REG_P (recog_data.operand[i])) 2209*e4b17023SJohn Marino { 2210*e4b17023SJohn Marino /* An input reg is implicitly popped if it is tied to an 2211*e4b17023SJohn Marino output, or if there is a CLOBBER for it. */ 2212*e4b17023SJohn Marino int j; 2213*e4b17023SJohn Marino 2214*e4b17023SJohn Marino for (j = 0; j < n_clobbers; j++) 2215*e4b17023SJohn Marino if (operands_match_p (clobber_reg[j], recog_data.operand[i])) 2216*e4b17023SJohn Marino break; 2217*e4b17023SJohn Marino 2218*e4b17023SJohn Marino if (j < n_clobbers || recog_op_alt[i][alt].matches >= 0) 2219*e4b17023SJohn Marino { 2220*e4b17023SJohn Marino /* recog_data.operand[i] might not be at the top of stack. 2221*e4b17023SJohn Marino But that's OK, because all we need to do is pop the 2222*e4b17023SJohn Marino right number of regs off of the top of the reg-stack. 2223*e4b17023SJohn Marino record_asm_stack_regs guaranteed that all implicitly 2224*e4b17023SJohn Marino popped regs were grouped at the top of the reg-stack. */ 2225*e4b17023SJohn Marino 2226*e4b17023SJohn Marino CLEAR_HARD_REG_BIT (regstack->reg_set, 2227*e4b17023SJohn Marino regstack->reg[regstack->top]); 2228*e4b17023SJohn Marino regstack->top--; 2229*e4b17023SJohn Marino } 2230*e4b17023SJohn Marino } 2231*e4b17023SJohn Marino 2232*e4b17023SJohn Marino /* Now add to REGSTACK any outputs that the asm implicitly pushed. 2233*e4b17023SJohn Marino Note that there isn't any need to substitute register numbers. 2234*e4b17023SJohn Marino ??? Explain why this is true. */ 2235*e4b17023SJohn Marino 2236*e4b17023SJohn Marino for (i = LAST_STACK_REG; i >= FIRST_STACK_REG; i--) 2237*e4b17023SJohn Marino { 2238*e4b17023SJohn Marino /* See if there is an output for this hard reg. */ 2239*e4b17023SJohn Marino int j; 2240*e4b17023SJohn Marino 2241*e4b17023SJohn Marino for (j = 0; j < n_outputs; j++) 2242*e4b17023SJohn Marino if (STACK_REG_P (recog_data.operand[j]) 2243*e4b17023SJohn Marino && REGNO (recog_data.operand[j]) == (unsigned) i) 2244*e4b17023SJohn Marino { 2245*e4b17023SJohn Marino regstack->reg[++regstack->top] = i; 2246*e4b17023SJohn Marino SET_HARD_REG_BIT (regstack->reg_set, i); 2247*e4b17023SJohn Marino break; 2248*e4b17023SJohn Marino } 2249*e4b17023SJohn Marino } 2250*e4b17023SJohn Marino 2251*e4b17023SJohn Marino /* Now emit a pop insn for any REG_UNUSED output, or any REG_DEAD 2252*e4b17023SJohn Marino input that the asm didn't implicitly pop. If the asm didn't 2253*e4b17023SJohn Marino implicitly pop an input reg, that reg will still be live. 2254*e4b17023SJohn Marino 2255*e4b17023SJohn Marino Note that we can't use find_regno_note here: the register numbers 2256*e4b17023SJohn Marino in the death notes have already been substituted. */ 2257*e4b17023SJohn Marino 2258*e4b17023SJohn Marino for (i = 0; i < n_outputs; i++) 2259*e4b17023SJohn Marino if (STACK_REG_P (recog_data.operand[i])) 2260*e4b17023SJohn Marino { 2261*e4b17023SJohn Marino int j; 2262*e4b17023SJohn Marino 2263*e4b17023SJohn Marino for (j = 0; j < n_notes; j++) 2264*e4b17023SJohn Marino if (REGNO (recog_data.operand[i]) == REGNO (note_reg[j]) 2265*e4b17023SJohn Marino && note_kind[j] == REG_UNUSED) 2266*e4b17023SJohn Marino { 2267*e4b17023SJohn Marino insn = emit_pop_insn (insn, regstack, recog_data.operand[i], 2268*e4b17023SJohn Marino EMIT_AFTER); 2269*e4b17023SJohn Marino break; 2270*e4b17023SJohn Marino } 2271*e4b17023SJohn Marino } 2272*e4b17023SJohn Marino 2273*e4b17023SJohn Marino for (i = n_outputs; i < n_outputs + n_inputs; i++) 2274*e4b17023SJohn Marino if (STACK_REG_P (recog_data.operand[i])) 2275*e4b17023SJohn Marino { 2276*e4b17023SJohn Marino int j; 2277*e4b17023SJohn Marino 2278*e4b17023SJohn Marino for (j = 0; j < n_notes; j++) 2279*e4b17023SJohn Marino if (REGNO (recog_data.operand[i]) == REGNO (note_reg[j]) 2280*e4b17023SJohn Marino && note_kind[j] == REG_DEAD 2281*e4b17023SJohn Marino && TEST_HARD_REG_BIT (regstack->reg_set, 2282*e4b17023SJohn Marino REGNO (recog_data.operand[i]))) 2283*e4b17023SJohn Marino { 2284*e4b17023SJohn Marino insn = emit_pop_insn (insn, regstack, recog_data.operand[i], 2285*e4b17023SJohn Marino EMIT_AFTER); 2286*e4b17023SJohn Marino break; 2287*e4b17023SJohn Marino } 2288*e4b17023SJohn Marino } 2289*e4b17023SJohn Marino } 2290*e4b17023SJohn Marino 2291*e4b17023SJohn Marino /* Substitute stack hard reg numbers for stack virtual registers in 2292*e4b17023SJohn Marino INSN. Non-stack register numbers are not changed. REGSTACK is the 2293*e4b17023SJohn Marino current stack content. Insns may be emitted as needed to arrange the 2294*e4b17023SJohn Marino stack for the 387 based on the contents of the insn. Return whether 2295*e4b17023SJohn Marino a control flow insn was deleted in the process. */ 2296*e4b17023SJohn Marino 2297*e4b17023SJohn Marino static bool 2298*e4b17023SJohn Marino subst_stack_regs (rtx insn, stack regstack) 2299*e4b17023SJohn Marino { 2300*e4b17023SJohn Marino rtx *note_link, note; 2301*e4b17023SJohn Marino bool control_flow_insn_deleted = false; 2302*e4b17023SJohn Marino int i; 2303*e4b17023SJohn Marino 2304*e4b17023SJohn Marino if (CALL_P (insn)) 2305*e4b17023SJohn Marino { 2306*e4b17023SJohn Marino int top = regstack->top; 2307*e4b17023SJohn Marino 2308*e4b17023SJohn Marino /* If there are any floating point parameters to be passed in 2309*e4b17023SJohn Marino registers for this call, make sure they are in the right 2310*e4b17023SJohn Marino order. */ 2311*e4b17023SJohn Marino 2312*e4b17023SJohn Marino if (top >= 0) 2313*e4b17023SJohn Marino { 2314*e4b17023SJohn Marino straighten_stack (insn, regstack); 2315*e4b17023SJohn Marino 2316*e4b17023SJohn Marino /* Now mark the arguments as dead after the call. */ 2317*e4b17023SJohn Marino 2318*e4b17023SJohn Marino while (regstack->top >= 0) 2319*e4b17023SJohn Marino { 2320*e4b17023SJohn Marino CLEAR_HARD_REG_BIT (regstack->reg_set, FIRST_STACK_REG + regstack->top); 2321*e4b17023SJohn Marino regstack->top--; 2322*e4b17023SJohn Marino } 2323*e4b17023SJohn Marino } 2324*e4b17023SJohn Marino } 2325*e4b17023SJohn Marino 2326*e4b17023SJohn Marino /* Do the actual substitution if any stack regs are mentioned. 2327*e4b17023SJohn Marino Since we only record whether entire insn mentions stack regs, and 2328*e4b17023SJohn Marino subst_stack_regs_pat only works for patterns that contain stack regs, 2329*e4b17023SJohn Marino we must check each pattern in a parallel here. A call_value_pop could 2330*e4b17023SJohn Marino fail otherwise. */ 2331*e4b17023SJohn Marino 2332*e4b17023SJohn Marino if (stack_regs_mentioned (insn)) 2333*e4b17023SJohn Marino { 2334*e4b17023SJohn Marino int n_operands = asm_noperands (PATTERN (insn)); 2335*e4b17023SJohn Marino if (n_operands >= 0) 2336*e4b17023SJohn Marino { 2337*e4b17023SJohn Marino /* This insn is an `asm' with operands. Decode the operands, 2338*e4b17023SJohn Marino decide how many are inputs, and do register substitution. 2339*e4b17023SJohn Marino Any REG_UNUSED notes will be handled by subst_asm_stack_regs. */ 2340*e4b17023SJohn Marino 2341*e4b17023SJohn Marino subst_asm_stack_regs (insn, regstack); 2342*e4b17023SJohn Marino return control_flow_insn_deleted; 2343*e4b17023SJohn Marino } 2344*e4b17023SJohn Marino 2345*e4b17023SJohn Marino if (GET_CODE (PATTERN (insn)) == PARALLEL) 2346*e4b17023SJohn Marino for (i = 0; i < XVECLEN (PATTERN (insn), 0); i++) 2347*e4b17023SJohn Marino { 2348*e4b17023SJohn Marino if (stack_regs_mentioned_p (XVECEXP (PATTERN (insn), 0, i))) 2349*e4b17023SJohn Marino { 2350*e4b17023SJohn Marino if (GET_CODE (XVECEXP (PATTERN (insn), 0, i)) == CLOBBER) 2351*e4b17023SJohn Marino XVECEXP (PATTERN (insn), 0, i) 2352*e4b17023SJohn Marino = shallow_copy_rtx (XVECEXP (PATTERN (insn), 0, i)); 2353*e4b17023SJohn Marino control_flow_insn_deleted 2354*e4b17023SJohn Marino |= subst_stack_regs_pat (insn, regstack, 2355*e4b17023SJohn Marino XVECEXP (PATTERN (insn), 0, i)); 2356*e4b17023SJohn Marino } 2357*e4b17023SJohn Marino } 2358*e4b17023SJohn Marino else 2359*e4b17023SJohn Marino control_flow_insn_deleted 2360*e4b17023SJohn Marino |= subst_stack_regs_pat (insn, regstack, PATTERN (insn)); 2361*e4b17023SJohn Marino } 2362*e4b17023SJohn Marino 2363*e4b17023SJohn Marino /* subst_stack_regs_pat may have deleted a no-op insn. If so, any 2364*e4b17023SJohn Marino REG_UNUSED will already have been dealt with, so just return. */ 2365*e4b17023SJohn Marino 2366*e4b17023SJohn Marino if (NOTE_P (insn) || INSN_DELETED_P (insn)) 2367*e4b17023SJohn Marino return control_flow_insn_deleted; 2368*e4b17023SJohn Marino 2369*e4b17023SJohn Marino /* If this a noreturn call, we can't insert pop insns after it. 2370*e4b17023SJohn Marino Instead, reset the stack state to empty. */ 2371*e4b17023SJohn Marino if (CALL_P (insn) 2372*e4b17023SJohn Marino && find_reg_note (insn, REG_NORETURN, NULL)) 2373*e4b17023SJohn Marino { 2374*e4b17023SJohn Marino regstack->top = -1; 2375*e4b17023SJohn Marino CLEAR_HARD_REG_SET (regstack->reg_set); 2376*e4b17023SJohn Marino return control_flow_insn_deleted; 2377*e4b17023SJohn Marino } 2378*e4b17023SJohn Marino 2379*e4b17023SJohn Marino /* If there is a REG_UNUSED note on a stack register on this insn, 2380*e4b17023SJohn Marino the indicated reg must be popped. The REG_UNUSED note is removed, 2381*e4b17023SJohn Marino since the form of the newly emitted pop insn references the reg, 2382*e4b17023SJohn Marino making it no longer `unset'. */ 2383*e4b17023SJohn Marino 2384*e4b17023SJohn Marino note_link = ®_NOTES (insn); 2385*e4b17023SJohn Marino for (note = *note_link; note; note = XEXP (note, 1)) 2386*e4b17023SJohn Marino if (REG_NOTE_KIND (note) == REG_UNUSED && STACK_REG_P (XEXP (note, 0))) 2387*e4b17023SJohn Marino { 2388*e4b17023SJohn Marino *note_link = XEXP (note, 1); 2389*e4b17023SJohn Marino insn = emit_pop_insn (insn, regstack, XEXP (note, 0), EMIT_AFTER); 2390*e4b17023SJohn Marino } 2391*e4b17023SJohn Marino else 2392*e4b17023SJohn Marino note_link = &XEXP (note, 1); 2393*e4b17023SJohn Marino 2394*e4b17023SJohn Marino return control_flow_insn_deleted; 2395*e4b17023SJohn Marino } 2396*e4b17023SJohn Marino 2397*e4b17023SJohn Marino /* Change the organization of the stack so that it fits a new basic 2398*e4b17023SJohn Marino block. Some registers might have to be popped, but there can never be 2399*e4b17023SJohn Marino a register live in the new block that is not now live. 2400*e4b17023SJohn Marino 2401*e4b17023SJohn Marino Insert any needed insns before or after INSN, as indicated by 2402*e4b17023SJohn Marino WHERE. OLD is the original stack layout, and NEW is the desired 2403*e4b17023SJohn Marino form. OLD is updated to reflect the code emitted, i.e., it will be 2404*e4b17023SJohn Marino the same as NEW upon return. 2405*e4b17023SJohn Marino 2406*e4b17023SJohn Marino This function will not preserve block_end[]. But that information 2407*e4b17023SJohn Marino is no longer needed once this has executed. */ 2408*e4b17023SJohn Marino 2409*e4b17023SJohn Marino static void 2410*e4b17023SJohn Marino change_stack (rtx insn, stack old, stack new_stack, enum emit_where where) 2411*e4b17023SJohn Marino { 2412*e4b17023SJohn Marino int reg; 2413*e4b17023SJohn Marino int update_end = 0; 2414*e4b17023SJohn Marino int i; 2415*e4b17023SJohn Marino 2416*e4b17023SJohn Marino /* Stack adjustments for the first insn in a block update the 2417*e4b17023SJohn Marino current_block's stack_in instead of inserting insns directly. 2418*e4b17023SJohn Marino compensate_edges will add the necessary code later. */ 2419*e4b17023SJohn Marino if (current_block 2420*e4b17023SJohn Marino && starting_stack_p 2421*e4b17023SJohn Marino && where == EMIT_BEFORE) 2422*e4b17023SJohn Marino { 2423*e4b17023SJohn Marino BLOCK_INFO (current_block)->stack_in = *new_stack; 2424*e4b17023SJohn Marino starting_stack_p = false; 2425*e4b17023SJohn Marino *old = *new_stack; 2426*e4b17023SJohn Marino return; 2427*e4b17023SJohn Marino } 2428*e4b17023SJohn Marino 2429*e4b17023SJohn Marino /* We will be inserting new insns "backwards". If we are to insert 2430*e4b17023SJohn Marino after INSN, find the next insn, and insert before it. */ 2431*e4b17023SJohn Marino 2432*e4b17023SJohn Marino if (where == EMIT_AFTER) 2433*e4b17023SJohn Marino { 2434*e4b17023SJohn Marino if (current_block && BB_END (current_block) == insn) 2435*e4b17023SJohn Marino update_end = 1; 2436*e4b17023SJohn Marino insn = NEXT_INSN (insn); 2437*e4b17023SJohn Marino } 2438*e4b17023SJohn Marino 2439*e4b17023SJohn Marino /* Initialize partially dead variables. */ 2440*e4b17023SJohn Marino for (i = FIRST_STACK_REG; i < LAST_STACK_REG + 1; i++) 2441*e4b17023SJohn Marino if (TEST_HARD_REG_BIT (new_stack->reg_set, i) 2442*e4b17023SJohn Marino && !TEST_HARD_REG_BIT (old->reg_set, i)) 2443*e4b17023SJohn Marino { 2444*e4b17023SJohn Marino old->reg[++old->top] = i; 2445*e4b17023SJohn Marino SET_HARD_REG_BIT (old->reg_set, i); 2446*e4b17023SJohn Marino emit_insn_before (gen_rtx_SET (VOIDmode, 2447*e4b17023SJohn Marino FP_MODE_REG (i, SFmode), not_a_num), insn); 2448*e4b17023SJohn Marino } 2449*e4b17023SJohn Marino 2450*e4b17023SJohn Marino /* Pop any registers that are not needed in the new block. */ 2451*e4b17023SJohn Marino 2452*e4b17023SJohn Marino /* If the destination block's stack already has a specified layout 2453*e4b17023SJohn Marino and contains two or more registers, use a more intelligent algorithm 2454*e4b17023SJohn Marino to pop registers that minimizes the number number of fxchs below. */ 2455*e4b17023SJohn Marino if (new_stack->top > 0) 2456*e4b17023SJohn Marino { 2457*e4b17023SJohn Marino bool slots[REG_STACK_SIZE]; 2458*e4b17023SJohn Marino int pops[REG_STACK_SIZE]; 2459*e4b17023SJohn Marino int next, dest, topsrc; 2460*e4b17023SJohn Marino 2461*e4b17023SJohn Marino /* First pass to determine the free slots. */ 2462*e4b17023SJohn Marino for (reg = 0; reg <= new_stack->top; reg++) 2463*e4b17023SJohn Marino slots[reg] = TEST_HARD_REG_BIT (new_stack->reg_set, old->reg[reg]); 2464*e4b17023SJohn Marino 2465*e4b17023SJohn Marino /* Second pass to allocate preferred slots. */ 2466*e4b17023SJohn Marino topsrc = -1; 2467*e4b17023SJohn Marino for (reg = old->top; reg > new_stack->top; reg--) 2468*e4b17023SJohn Marino if (TEST_HARD_REG_BIT (new_stack->reg_set, old->reg[reg])) 2469*e4b17023SJohn Marino { 2470*e4b17023SJohn Marino dest = -1; 2471*e4b17023SJohn Marino for (next = 0; next <= new_stack->top; next++) 2472*e4b17023SJohn Marino if (!slots[next] && new_stack->reg[next] == old->reg[reg]) 2473*e4b17023SJohn Marino { 2474*e4b17023SJohn Marino /* If this is a preference for the new top of stack, record 2475*e4b17023SJohn Marino the fact by remembering it's old->reg in topsrc. */ 2476*e4b17023SJohn Marino if (next == new_stack->top) 2477*e4b17023SJohn Marino topsrc = reg; 2478*e4b17023SJohn Marino slots[next] = true; 2479*e4b17023SJohn Marino dest = next; 2480*e4b17023SJohn Marino break; 2481*e4b17023SJohn Marino } 2482*e4b17023SJohn Marino pops[reg] = dest; 2483*e4b17023SJohn Marino } 2484*e4b17023SJohn Marino else 2485*e4b17023SJohn Marino pops[reg] = reg; 2486*e4b17023SJohn Marino 2487*e4b17023SJohn Marino /* Intentionally, avoid placing the top of stack in it's correct 2488*e4b17023SJohn Marino location, if we still need to permute the stack below and we 2489*e4b17023SJohn Marino can usefully place it somewhere else. This is the case if any 2490*e4b17023SJohn Marino slot is still unallocated, in which case we should place the 2491*e4b17023SJohn Marino top of stack there. */ 2492*e4b17023SJohn Marino if (topsrc != -1) 2493*e4b17023SJohn Marino for (reg = 0; reg < new_stack->top; reg++) 2494*e4b17023SJohn Marino if (!slots[reg]) 2495*e4b17023SJohn Marino { 2496*e4b17023SJohn Marino pops[topsrc] = reg; 2497*e4b17023SJohn Marino slots[new_stack->top] = false; 2498*e4b17023SJohn Marino slots[reg] = true; 2499*e4b17023SJohn Marino break; 2500*e4b17023SJohn Marino } 2501*e4b17023SJohn Marino 2502*e4b17023SJohn Marino /* Third pass allocates remaining slots and emits pop insns. */ 2503*e4b17023SJohn Marino next = new_stack->top; 2504*e4b17023SJohn Marino for (reg = old->top; reg > new_stack->top; reg--) 2505*e4b17023SJohn Marino { 2506*e4b17023SJohn Marino dest = pops[reg]; 2507*e4b17023SJohn Marino if (dest == -1) 2508*e4b17023SJohn Marino { 2509*e4b17023SJohn Marino /* Find next free slot. */ 2510*e4b17023SJohn Marino while (slots[next]) 2511*e4b17023SJohn Marino next--; 2512*e4b17023SJohn Marino dest = next--; 2513*e4b17023SJohn Marino } 2514*e4b17023SJohn Marino emit_pop_insn (insn, old, FP_MODE_REG (old->reg[dest], DFmode), 2515*e4b17023SJohn Marino EMIT_BEFORE); 2516*e4b17023SJohn Marino } 2517*e4b17023SJohn Marino } 2518*e4b17023SJohn Marino else 2519*e4b17023SJohn Marino { 2520*e4b17023SJohn Marino /* The following loop attempts to maximize the number of times we 2521*e4b17023SJohn Marino pop the top of the stack, as this permits the use of the faster 2522*e4b17023SJohn Marino ffreep instruction on platforms that support it. */ 2523*e4b17023SJohn Marino int live, next; 2524*e4b17023SJohn Marino 2525*e4b17023SJohn Marino live = 0; 2526*e4b17023SJohn Marino for (reg = 0; reg <= old->top; reg++) 2527*e4b17023SJohn Marino if (TEST_HARD_REG_BIT (new_stack->reg_set, old->reg[reg])) 2528*e4b17023SJohn Marino live++; 2529*e4b17023SJohn Marino 2530*e4b17023SJohn Marino next = live; 2531*e4b17023SJohn Marino while (old->top >= live) 2532*e4b17023SJohn Marino if (TEST_HARD_REG_BIT (new_stack->reg_set, old->reg[old->top])) 2533*e4b17023SJohn Marino { 2534*e4b17023SJohn Marino while (TEST_HARD_REG_BIT (new_stack->reg_set, old->reg[next])) 2535*e4b17023SJohn Marino next--; 2536*e4b17023SJohn Marino emit_pop_insn (insn, old, FP_MODE_REG (old->reg[next], DFmode), 2537*e4b17023SJohn Marino EMIT_BEFORE); 2538*e4b17023SJohn Marino } 2539*e4b17023SJohn Marino else 2540*e4b17023SJohn Marino emit_pop_insn (insn, old, FP_MODE_REG (old->reg[old->top], DFmode), 2541*e4b17023SJohn Marino EMIT_BEFORE); 2542*e4b17023SJohn Marino } 2543*e4b17023SJohn Marino 2544*e4b17023SJohn Marino if (new_stack->top == -2) 2545*e4b17023SJohn Marino { 2546*e4b17023SJohn Marino /* If the new block has never been processed, then it can inherit 2547*e4b17023SJohn Marino the old stack order. */ 2548*e4b17023SJohn Marino 2549*e4b17023SJohn Marino new_stack->top = old->top; 2550*e4b17023SJohn Marino memcpy (new_stack->reg, old->reg, sizeof (new_stack->reg)); 2551*e4b17023SJohn Marino } 2552*e4b17023SJohn Marino else 2553*e4b17023SJohn Marino { 2554*e4b17023SJohn Marino /* This block has been entered before, and we must match the 2555*e4b17023SJohn Marino previously selected stack order. */ 2556*e4b17023SJohn Marino 2557*e4b17023SJohn Marino /* By now, the only difference should be the order of the stack, 2558*e4b17023SJohn Marino not their depth or liveliness. */ 2559*e4b17023SJohn Marino 2560*e4b17023SJohn Marino gcc_assert (hard_reg_set_equal_p (old->reg_set, new_stack->reg_set)); 2561*e4b17023SJohn Marino gcc_assert (old->top == new_stack->top); 2562*e4b17023SJohn Marino 2563*e4b17023SJohn Marino /* If the stack is not empty (new_stack->top != -1), loop here emitting 2564*e4b17023SJohn Marino swaps until the stack is correct. 2565*e4b17023SJohn Marino 2566*e4b17023SJohn Marino The worst case number of swaps emitted is N + 2, where N is the 2567*e4b17023SJohn Marino depth of the stack. In some cases, the reg at the top of 2568*e4b17023SJohn Marino stack may be correct, but swapped anyway in order to fix 2569*e4b17023SJohn Marino other regs. But since we never swap any other reg away from 2570*e4b17023SJohn Marino its correct slot, this algorithm will converge. */ 2571*e4b17023SJohn Marino 2572*e4b17023SJohn Marino if (new_stack->top != -1) 2573*e4b17023SJohn Marino do 2574*e4b17023SJohn Marino { 2575*e4b17023SJohn Marino /* Swap the reg at top of stack into the position it is 2576*e4b17023SJohn Marino supposed to be in, until the correct top of stack appears. */ 2577*e4b17023SJohn Marino 2578*e4b17023SJohn Marino while (old->reg[old->top] != new_stack->reg[new_stack->top]) 2579*e4b17023SJohn Marino { 2580*e4b17023SJohn Marino for (reg = new_stack->top; reg >= 0; reg--) 2581*e4b17023SJohn Marino if (new_stack->reg[reg] == old->reg[old->top]) 2582*e4b17023SJohn Marino break; 2583*e4b17023SJohn Marino 2584*e4b17023SJohn Marino gcc_assert (reg != -1); 2585*e4b17023SJohn Marino 2586*e4b17023SJohn Marino emit_swap_insn (insn, old, 2587*e4b17023SJohn Marino FP_MODE_REG (old->reg[reg], DFmode)); 2588*e4b17023SJohn Marino } 2589*e4b17023SJohn Marino 2590*e4b17023SJohn Marino /* See if any regs remain incorrect. If so, bring an 2591*e4b17023SJohn Marino incorrect reg to the top of stack, and let the while loop 2592*e4b17023SJohn Marino above fix it. */ 2593*e4b17023SJohn Marino 2594*e4b17023SJohn Marino for (reg = new_stack->top; reg >= 0; reg--) 2595*e4b17023SJohn Marino if (new_stack->reg[reg] != old->reg[reg]) 2596*e4b17023SJohn Marino { 2597*e4b17023SJohn Marino emit_swap_insn (insn, old, 2598*e4b17023SJohn Marino FP_MODE_REG (old->reg[reg], DFmode)); 2599*e4b17023SJohn Marino break; 2600*e4b17023SJohn Marino } 2601*e4b17023SJohn Marino } while (reg >= 0); 2602*e4b17023SJohn Marino 2603*e4b17023SJohn Marino /* At this point there must be no differences. */ 2604*e4b17023SJohn Marino 2605*e4b17023SJohn Marino for (reg = old->top; reg >= 0; reg--) 2606*e4b17023SJohn Marino gcc_assert (old->reg[reg] == new_stack->reg[reg]); 2607*e4b17023SJohn Marino } 2608*e4b17023SJohn Marino 2609*e4b17023SJohn Marino if (update_end) 2610*e4b17023SJohn Marino BB_END (current_block) = PREV_INSN (insn); 2611*e4b17023SJohn Marino } 2612*e4b17023SJohn Marino 2613*e4b17023SJohn Marino /* Print stack configuration. */ 2614*e4b17023SJohn Marino 2615*e4b17023SJohn Marino static void 2616*e4b17023SJohn Marino print_stack (FILE *file, stack s) 2617*e4b17023SJohn Marino { 2618*e4b17023SJohn Marino if (! file) 2619*e4b17023SJohn Marino return; 2620*e4b17023SJohn Marino 2621*e4b17023SJohn Marino if (s->top == -2) 2622*e4b17023SJohn Marino fprintf (file, "uninitialized\n"); 2623*e4b17023SJohn Marino else if (s->top == -1) 2624*e4b17023SJohn Marino fprintf (file, "empty\n"); 2625*e4b17023SJohn Marino else 2626*e4b17023SJohn Marino { 2627*e4b17023SJohn Marino int i; 2628*e4b17023SJohn Marino fputs ("[ ", file); 2629*e4b17023SJohn Marino for (i = 0; i <= s->top; ++i) 2630*e4b17023SJohn Marino fprintf (file, "%d ", s->reg[i]); 2631*e4b17023SJohn Marino fputs ("]\n", file); 2632*e4b17023SJohn Marino } 2633*e4b17023SJohn Marino } 2634*e4b17023SJohn Marino 2635*e4b17023SJohn Marino /* This function was doing life analysis. We now let the regular live 2636*e4b17023SJohn Marino code do it's job, so we only need to check some extra invariants 2637*e4b17023SJohn Marino that reg-stack expects. Primary among these being that all registers 2638*e4b17023SJohn Marino are initialized before use. 2639*e4b17023SJohn Marino 2640*e4b17023SJohn Marino The function returns true when code was emitted to CFG edges and 2641*e4b17023SJohn Marino commit_edge_insertions needs to be called. */ 2642*e4b17023SJohn Marino 2643*e4b17023SJohn Marino static int 2644*e4b17023SJohn Marino convert_regs_entry (void) 2645*e4b17023SJohn Marino { 2646*e4b17023SJohn Marino int inserted = 0; 2647*e4b17023SJohn Marino edge e; 2648*e4b17023SJohn Marino edge_iterator ei; 2649*e4b17023SJohn Marino 2650*e4b17023SJohn Marino /* Load something into each stack register live at function entry. 2651*e4b17023SJohn Marino Such live registers can be caused by uninitialized variables or 2652*e4b17023SJohn Marino functions not returning values on all paths. In order to keep 2653*e4b17023SJohn Marino the push/pop code happy, and to not scrog the register stack, we 2654*e4b17023SJohn Marino must put something in these registers. Use a QNaN. 2655*e4b17023SJohn Marino 2656*e4b17023SJohn Marino Note that we are inserting converted code here. This code is 2657*e4b17023SJohn Marino never seen by the convert_regs pass. */ 2658*e4b17023SJohn Marino 2659*e4b17023SJohn Marino FOR_EACH_EDGE (e, ei, ENTRY_BLOCK_PTR->succs) 2660*e4b17023SJohn Marino { 2661*e4b17023SJohn Marino basic_block block = e->dest; 2662*e4b17023SJohn Marino block_info bi = BLOCK_INFO (block); 2663*e4b17023SJohn Marino int reg, top = -1; 2664*e4b17023SJohn Marino 2665*e4b17023SJohn Marino for (reg = LAST_STACK_REG; reg >= FIRST_STACK_REG; --reg) 2666*e4b17023SJohn Marino if (TEST_HARD_REG_BIT (bi->stack_in.reg_set, reg)) 2667*e4b17023SJohn Marino { 2668*e4b17023SJohn Marino rtx init; 2669*e4b17023SJohn Marino 2670*e4b17023SJohn Marino bi->stack_in.reg[++top] = reg; 2671*e4b17023SJohn Marino 2672*e4b17023SJohn Marino init = gen_rtx_SET (VOIDmode, 2673*e4b17023SJohn Marino FP_MODE_REG (FIRST_STACK_REG, SFmode), 2674*e4b17023SJohn Marino not_a_num); 2675*e4b17023SJohn Marino insert_insn_on_edge (init, e); 2676*e4b17023SJohn Marino inserted = 1; 2677*e4b17023SJohn Marino } 2678*e4b17023SJohn Marino 2679*e4b17023SJohn Marino bi->stack_in.top = top; 2680*e4b17023SJohn Marino } 2681*e4b17023SJohn Marino 2682*e4b17023SJohn Marino return inserted; 2683*e4b17023SJohn Marino } 2684*e4b17023SJohn Marino 2685*e4b17023SJohn Marino /* Construct the desired stack for function exit. This will either 2686*e4b17023SJohn Marino be `empty', or the function return value at top-of-stack. */ 2687*e4b17023SJohn Marino 2688*e4b17023SJohn Marino static void 2689*e4b17023SJohn Marino convert_regs_exit (void) 2690*e4b17023SJohn Marino { 2691*e4b17023SJohn Marino int value_reg_low, value_reg_high; 2692*e4b17023SJohn Marino stack output_stack; 2693*e4b17023SJohn Marino rtx retvalue; 2694*e4b17023SJohn Marino 2695*e4b17023SJohn Marino retvalue = stack_result (current_function_decl); 2696*e4b17023SJohn Marino value_reg_low = value_reg_high = -1; 2697*e4b17023SJohn Marino if (retvalue) 2698*e4b17023SJohn Marino { 2699*e4b17023SJohn Marino value_reg_low = REGNO (retvalue); 2700*e4b17023SJohn Marino value_reg_high = END_HARD_REGNO (retvalue) - 1; 2701*e4b17023SJohn Marino } 2702*e4b17023SJohn Marino 2703*e4b17023SJohn Marino output_stack = &BLOCK_INFO (EXIT_BLOCK_PTR)->stack_in; 2704*e4b17023SJohn Marino if (value_reg_low == -1) 2705*e4b17023SJohn Marino output_stack->top = -1; 2706*e4b17023SJohn Marino else 2707*e4b17023SJohn Marino { 2708*e4b17023SJohn Marino int reg; 2709*e4b17023SJohn Marino 2710*e4b17023SJohn Marino output_stack->top = value_reg_high - value_reg_low; 2711*e4b17023SJohn Marino for (reg = value_reg_low; reg <= value_reg_high; ++reg) 2712*e4b17023SJohn Marino { 2713*e4b17023SJohn Marino output_stack->reg[value_reg_high - reg] = reg; 2714*e4b17023SJohn Marino SET_HARD_REG_BIT (output_stack->reg_set, reg); 2715*e4b17023SJohn Marino } 2716*e4b17023SJohn Marino } 2717*e4b17023SJohn Marino } 2718*e4b17023SJohn Marino 2719*e4b17023SJohn Marino /* Copy the stack info from the end of edge E's source block to the 2720*e4b17023SJohn Marino start of E's destination block. */ 2721*e4b17023SJohn Marino 2722*e4b17023SJohn Marino static void 2723*e4b17023SJohn Marino propagate_stack (edge e) 2724*e4b17023SJohn Marino { 2725*e4b17023SJohn Marino stack src_stack = &BLOCK_INFO (e->src)->stack_out; 2726*e4b17023SJohn Marino stack dest_stack = &BLOCK_INFO (e->dest)->stack_in; 2727*e4b17023SJohn Marino int reg; 2728*e4b17023SJohn Marino 2729*e4b17023SJohn Marino /* Preserve the order of the original stack, but check whether 2730*e4b17023SJohn Marino any pops are needed. */ 2731*e4b17023SJohn Marino dest_stack->top = -1; 2732*e4b17023SJohn Marino for (reg = 0; reg <= src_stack->top; ++reg) 2733*e4b17023SJohn Marino if (TEST_HARD_REG_BIT (dest_stack->reg_set, src_stack->reg[reg])) 2734*e4b17023SJohn Marino dest_stack->reg[++dest_stack->top] = src_stack->reg[reg]; 2735*e4b17023SJohn Marino 2736*e4b17023SJohn Marino /* Push in any partially dead values. */ 2737*e4b17023SJohn Marino for (reg = FIRST_STACK_REG; reg < LAST_STACK_REG + 1; reg++) 2738*e4b17023SJohn Marino if (TEST_HARD_REG_BIT (dest_stack->reg_set, reg) 2739*e4b17023SJohn Marino && !TEST_HARD_REG_BIT (src_stack->reg_set, reg)) 2740*e4b17023SJohn Marino dest_stack->reg[++dest_stack->top] = reg; 2741*e4b17023SJohn Marino } 2742*e4b17023SJohn Marino 2743*e4b17023SJohn Marino 2744*e4b17023SJohn Marino /* Adjust the stack of edge E's source block on exit to match the stack 2745*e4b17023SJohn Marino of it's target block upon input. The stack layouts of both blocks 2746*e4b17023SJohn Marino should have been defined by now. */ 2747*e4b17023SJohn Marino 2748*e4b17023SJohn Marino static bool 2749*e4b17023SJohn Marino compensate_edge (edge e) 2750*e4b17023SJohn Marino { 2751*e4b17023SJohn Marino basic_block source = e->src, target = e->dest; 2752*e4b17023SJohn Marino stack target_stack = &BLOCK_INFO (target)->stack_in; 2753*e4b17023SJohn Marino stack source_stack = &BLOCK_INFO (source)->stack_out; 2754*e4b17023SJohn Marino struct stack_def regstack; 2755*e4b17023SJohn Marino int reg; 2756*e4b17023SJohn Marino 2757*e4b17023SJohn Marino if (dump_file) 2758*e4b17023SJohn Marino fprintf (dump_file, "Edge %d->%d: ", source->index, target->index); 2759*e4b17023SJohn Marino 2760*e4b17023SJohn Marino gcc_assert (target_stack->top != -2); 2761*e4b17023SJohn Marino 2762*e4b17023SJohn Marino /* Check whether stacks are identical. */ 2763*e4b17023SJohn Marino if (target_stack->top == source_stack->top) 2764*e4b17023SJohn Marino { 2765*e4b17023SJohn Marino for (reg = target_stack->top; reg >= 0; --reg) 2766*e4b17023SJohn Marino if (target_stack->reg[reg] != source_stack->reg[reg]) 2767*e4b17023SJohn Marino break; 2768*e4b17023SJohn Marino 2769*e4b17023SJohn Marino if (reg == -1) 2770*e4b17023SJohn Marino { 2771*e4b17023SJohn Marino if (dump_file) 2772*e4b17023SJohn Marino fprintf (dump_file, "no changes needed\n"); 2773*e4b17023SJohn Marino return false; 2774*e4b17023SJohn Marino } 2775*e4b17023SJohn Marino } 2776*e4b17023SJohn Marino 2777*e4b17023SJohn Marino if (dump_file) 2778*e4b17023SJohn Marino { 2779*e4b17023SJohn Marino fprintf (dump_file, "correcting stack to "); 2780*e4b17023SJohn Marino print_stack (dump_file, target_stack); 2781*e4b17023SJohn Marino } 2782*e4b17023SJohn Marino 2783*e4b17023SJohn Marino /* Abnormal calls may appear to have values live in st(0), but the 2784*e4b17023SJohn Marino abnormal return path will not have actually loaded the values. */ 2785*e4b17023SJohn Marino if (e->flags & EDGE_ABNORMAL_CALL) 2786*e4b17023SJohn Marino { 2787*e4b17023SJohn Marino /* Assert that the lifetimes are as we expect -- one value 2788*e4b17023SJohn Marino live at st(0) on the end of the source block, and no 2789*e4b17023SJohn Marino values live at the beginning of the destination block. 2790*e4b17023SJohn Marino For complex return values, we may have st(1) live as well. */ 2791*e4b17023SJohn Marino gcc_assert (source_stack->top == 0 || source_stack->top == 1); 2792*e4b17023SJohn Marino gcc_assert (target_stack->top == -1); 2793*e4b17023SJohn Marino return false; 2794*e4b17023SJohn Marino } 2795*e4b17023SJohn Marino 2796*e4b17023SJohn Marino /* Handle non-call EH edges specially. The normal return path have 2797*e4b17023SJohn Marino values in registers. These will be popped en masse by the unwind 2798*e4b17023SJohn Marino library. */ 2799*e4b17023SJohn Marino if (e->flags & EDGE_EH) 2800*e4b17023SJohn Marino { 2801*e4b17023SJohn Marino gcc_assert (target_stack->top == -1); 2802*e4b17023SJohn Marino return false; 2803*e4b17023SJohn Marino } 2804*e4b17023SJohn Marino 2805*e4b17023SJohn Marino /* We don't support abnormal edges. Global takes care to 2806*e4b17023SJohn Marino avoid any live register across them, so we should never 2807*e4b17023SJohn Marino have to insert instructions on such edges. */ 2808*e4b17023SJohn Marino gcc_assert (! (e->flags & EDGE_ABNORMAL)); 2809*e4b17023SJohn Marino 2810*e4b17023SJohn Marino /* Make a copy of source_stack as change_stack is destructive. */ 2811*e4b17023SJohn Marino regstack = *source_stack; 2812*e4b17023SJohn Marino 2813*e4b17023SJohn Marino /* It is better to output directly to the end of the block 2814*e4b17023SJohn Marino instead of to the edge, because emit_swap can do minimal 2815*e4b17023SJohn Marino insn scheduling. We can do this when there is only one 2816*e4b17023SJohn Marino edge out, and it is not abnormal. */ 2817*e4b17023SJohn Marino if (EDGE_COUNT (source->succs) == 1) 2818*e4b17023SJohn Marino { 2819*e4b17023SJohn Marino current_block = source; 2820*e4b17023SJohn Marino change_stack (BB_END (source), ®stack, target_stack, 2821*e4b17023SJohn Marino (JUMP_P (BB_END (source)) ? EMIT_BEFORE : EMIT_AFTER)); 2822*e4b17023SJohn Marino } 2823*e4b17023SJohn Marino else 2824*e4b17023SJohn Marino { 2825*e4b17023SJohn Marino rtx seq, after; 2826*e4b17023SJohn Marino 2827*e4b17023SJohn Marino current_block = NULL; 2828*e4b17023SJohn Marino start_sequence (); 2829*e4b17023SJohn Marino 2830*e4b17023SJohn Marino /* ??? change_stack needs some point to emit insns after. */ 2831*e4b17023SJohn Marino after = emit_note (NOTE_INSN_DELETED); 2832*e4b17023SJohn Marino 2833*e4b17023SJohn Marino change_stack (after, ®stack, target_stack, EMIT_BEFORE); 2834*e4b17023SJohn Marino 2835*e4b17023SJohn Marino seq = get_insns (); 2836*e4b17023SJohn Marino end_sequence (); 2837*e4b17023SJohn Marino 2838*e4b17023SJohn Marino insert_insn_on_edge (seq, e); 2839*e4b17023SJohn Marino return true; 2840*e4b17023SJohn Marino } 2841*e4b17023SJohn Marino return false; 2842*e4b17023SJohn Marino } 2843*e4b17023SJohn Marino 2844*e4b17023SJohn Marino /* Traverse all non-entry edges in the CFG, and emit the necessary 2845*e4b17023SJohn Marino edge compensation code to change the stack from stack_out of the 2846*e4b17023SJohn Marino source block to the stack_in of the destination block. */ 2847*e4b17023SJohn Marino 2848*e4b17023SJohn Marino static bool 2849*e4b17023SJohn Marino compensate_edges (void) 2850*e4b17023SJohn Marino { 2851*e4b17023SJohn Marino bool inserted = false; 2852*e4b17023SJohn Marino basic_block bb; 2853*e4b17023SJohn Marino 2854*e4b17023SJohn Marino starting_stack_p = false; 2855*e4b17023SJohn Marino 2856*e4b17023SJohn Marino FOR_EACH_BB (bb) 2857*e4b17023SJohn Marino if (bb != ENTRY_BLOCK_PTR) 2858*e4b17023SJohn Marino { 2859*e4b17023SJohn Marino edge e; 2860*e4b17023SJohn Marino edge_iterator ei; 2861*e4b17023SJohn Marino 2862*e4b17023SJohn Marino FOR_EACH_EDGE (e, ei, bb->succs) 2863*e4b17023SJohn Marino inserted |= compensate_edge (e); 2864*e4b17023SJohn Marino } 2865*e4b17023SJohn Marino return inserted; 2866*e4b17023SJohn Marino } 2867*e4b17023SJohn Marino 2868*e4b17023SJohn Marino /* Select the better of two edges E1 and E2 to use to determine the 2869*e4b17023SJohn Marino stack layout for their shared destination basic block. This is 2870*e4b17023SJohn Marino typically the more frequently executed. The edge E1 may be NULL 2871*e4b17023SJohn Marino (in which case E2 is returned), but E2 is always non-NULL. */ 2872*e4b17023SJohn Marino 2873*e4b17023SJohn Marino static edge 2874*e4b17023SJohn Marino better_edge (edge e1, edge e2) 2875*e4b17023SJohn Marino { 2876*e4b17023SJohn Marino if (!e1) 2877*e4b17023SJohn Marino return e2; 2878*e4b17023SJohn Marino 2879*e4b17023SJohn Marino if (EDGE_FREQUENCY (e1) > EDGE_FREQUENCY (e2)) 2880*e4b17023SJohn Marino return e1; 2881*e4b17023SJohn Marino if (EDGE_FREQUENCY (e1) < EDGE_FREQUENCY (e2)) 2882*e4b17023SJohn Marino return e2; 2883*e4b17023SJohn Marino 2884*e4b17023SJohn Marino if (e1->count > e2->count) 2885*e4b17023SJohn Marino return e1; 2886*e4b17023SJohn Marino if (e1->count < e2->count) 2887*e4b17023SJohn Marino return e2; 2888*e4b17023SJohn Marino 2889*e4b17023SJohn Marino /* Prefer critical edges to minimize inserting compensation code on 2890*e4b17023SJohn Marino critical edges. */ 2891*e4b17023SJohn Marino 2892*e4b17023SJohn Marino if (EDGE_CRITICAL_P (e1) != EDGE_CRITICAL_P (e2)) 2893*e4b17023SJohn Marino return EDGE_CRITICAL_P (e1) ? e1 : e2; 2894*e4b17023SJohn Marino 2895*e4b17023SJohn Marino /* Avoid non-deterministic behavior. */ 2896*e4b17023SJohn Marino return (e1->src->index < e2->src->index) ? e1 : e2; 2897*e4b17023SJohn Marino } 2898*e4b17023SJohn Marino 2899*e4b17023SJohn Marino /* Convert stack register references in one block. Return true if the CFG 2900*e4b17023SJohn Marino has been modified in the process. */ 2901*e4b17023SJohn Marino 2902*e4b17023SJohn Marino static bool 2903*e4b17023SJohn Marino convert_regs_1 (basic_block block) 2904*e4b17023SJohn Marino { 2905*e4b17023SJohn Marino struct stack_def regstack; 2906*e4b17023SJohn Marino block_info bi = BLOCK_INFO (block); 2907*e4b17023SJohn Marino int reg; 2908*e4b17023SJohn Marino rtx insn, next; 2909*e4b17023SJohn Marino bool control_flow_insn_deleted = false; 2910*e4b17023SJohn Marino bool cfg_altered = false; 2911*e4b17023SJohn Marino int debug_insns_with_starting_stack = 0; 2912*e4b17023SJohn Marino 2913*e4b17023SJohn Marino any_malformed_asm = false; 2914*e4b17023SJohn Marino 2915*e4b17023SJohn Marino /* Choose an initial stack layout, if one hasn't already been chosen. */ 2916*e4b17023SJohn Marino if (bi->stack_in.top == -2) 2917*e4b17023SJohn Marino { 2918*e4b17023SJohn Marino edge e, beste = NULL; 2919*e4b17023SJohn Marino edge_iterator ei; 2920*e4b17023SJohn Marino 2921*e4b17023SJohn Marino /* Select the best incoming edge (typically the most frequent) to 2922*e4b17023SJohn Marino use as a template for this basic block. */ 2923*e4b17023SJohn Marino FOR_EACH_EDGE (e, ei, block->preds) 2924*e4b17023SJohn Marino if (BLOCK_INFO (e->src)->done) 2925*e4b17023SJohn Marino beste = better_edge (beste, e); 2926*e4b17023SJohn Marino 2927*e4b17023SJohn Marino if (beste) 2928*e4b17023SJohn Marino propagate_stack (beste); 2929*e4b17023SJohn Marino else 2930*e4b17023SJohn Marino { 2931*e4b17023SJohn Marino /* No predecessors. Create an arbitrary input stack. */ 2932*e4b17023SJohn Marino bi->stack_in.top = -1; 2933*e4b17023SJohn Marino for (reg = LAST_STACK_REG; reg >= FIRST_STACK_REG; --reg) 2934*e4b17023SJohn Marino if (TEST_HARD_REG_BIT (bi->stack_in.reg_set, reg)) 2935*e4b17023SJohn Marino bi->stack_in.reg[++bi->stack_in.top] = reg; 2936*e4b17023SJohn Marino } 2937*e4b17023SJohn Marino } 2938*e4b17023SJohn Marino 2939*e4b17023SJohn Marino if (dump_file) 2940*e4b17023SJohn Marino { 2941*e4b17023SJohn Marino fprintf (dump_file, "\nBasic block %d\nInput stack: ", block->index); 2942*e4b17023SJohn Marino print_stack (dump_file, &bi->stack_in); 2943*e4b17023SJohn Marino } 2944*e4b17023SJohn Marino 2945*e4b17023SJohn Marino /* Process all insns in this block. Keep track of NEXT so that we 2946*e4b17023SJohn Marino don't process insns emitted while substituting in INSN. */ 2947*e4b17023SJohn Marino current_block = block; 2948*e4b17023SJohn Marino next = BB_HEAD (block); 2949*e4b17023SJohn Marino regstack = bi->stack_in; 2950*e4b17023SJohn Marino starting_stack_p = true; 2951*e4b17023SJohn Marino 2952*e4b17023SJohn Marino do 2953*e4b17023SJohn Marino { 2954*e4b17023SJohn Marino insn = next; 2955*e4b17023SJohn Marino next = NEXT_INSN (insn); 2956*e4b17023SJohn Marino 2957*e4b17023SJohn Marino /* Ensure we have not missed a block boundary. */ 2958*e4b17023SJohn Marino gcc_assert (next); 2959*e4b17023SJohn Marino if (insn == BB_END (block)) 2960*e4b17023SJohn Marino next = NULL; 2961*e4b17023SJohn Marino 2962*e4b17023SJohn Marino /* Don't bother processing unless there is a stack reg 2963*e4b17023SJohn Marino mentioned or if it's a CALL_INSN. */ 2964*e4b17023SJohn Marino if (DEBUG_INSN_P (insn)) 2965*e4b17023SJohn Marino { 2966*e4b17023SJohn Marino if (starting_stack_p) 2967*e4b17023SJohn Marino debug_insns_with_starting_stack++; 2968*e4b17023SJohn Marino else 2969*e4b17023SJohn Marino { 2970*e4b17023SJohn Marino subst_all_stack_regs_in_debug_insn (insn, ®stack); 2971*e4b17023SJohn Marino 2972*e4b17023SJohn Marino /* Nothing must ever die at a debug insn. If something 2973*e4b17023SJohn Marino is referenced in it that becomes dead, it should have 2974*e4b17023SJohn Marino died before and the reference in the debug insn 2975*e4b17023SJohn Marino should have been removed so as to avoid changing code 2976*e4b17023SJohn Marino generation. */ 2977*e4b17023SJohn Marino gcc_assert (!find_reg_note (insn, REG_DEAD, NULL)); 2978*e4b17023SJohn Marino } 2979*e4b17023SJohn Marino } 2980*e4b17023SJohn Marino else if (stack_regs_mentioned (insn) 2981*e4b17023SJohn Marino || CALL_P (insn)) 2982*e4b17023SJohn Marino { 2983*e4b17023SJohn Marino if (dump_file) 2984*e4b17023SJohn Marino { 2985*e4b17023SJohn Marino fprintf (dump_file, " insn %d input stack: ", 2986*e4b17023SJohn Marino INSN_UID (insn)); 2987*e4b17023SJohn Marino print_stack (dump_file, ®stack); 2988*e4b17023SJohn Marino } 2989*e4b17023SJohn Marino control_flow_insn_deleted |= subst_stack_regs (insn, ®stack); 2990*e4b17023SJohn Marino starting_stack_p = false; 2991*e4b17023SJohn Marino } 2992*e4b17023SJohn Marino } 2993*e4b17023SJohn Marino while (next); 2994*e4b17023SJohn Marino 2995*e4b17023SJohn Marino if (debug_insns_with_starting_stack) 2996*e4b17023SJohn Marino { 2997*e4b17023SJohn Marino /* Since it's the first non-debug instruction that determines 2998*e4b17023SJohn Marino the stack requirements of the current basic block, we refrain 2999*e4b17023SJohn Marino from updating debug insns before it in the loop above, and 3000*e4b17023SJohn Marino fix them up here. */ 3001*e4b17023SJohn Marino for (insn = BB_HEAD (block); debug_insns_with_starting_stack; 3002*e4b17023SJohn Marino insn = NEXT_INSN (insn)) 3003*e4b17023SJohn Marino { 3004*e4b17023SJohn Marino if (!DEBUG_INSN_P (insn)) 3005*e4b17023SJohn Marino continue; 3006*e4b17023SJohn Marino 3007*e4b17023SJohn Marino debug_insns_with_starting_stack--; 3008*e4b17023SJohn Marino subst_all_stack_regs_in_debug_insn (insn, &bi->stack_in); 3009*e4b17023SJohn Marino } 3010*e4b17023SJohn Marino } 3011*e4b17023SJohn Marino 3012*e4b17023SJohn Marino if (dump_file) 3013*e4b17023SJohn Marino { 3014*e4b17023SJohn Marino fprintf (dump_file, "Expected live registers ["); 3015*e4b17023SJohn Marino for (reg = FIRST_STACK_REG; reg <= LAST_STACK_REG; ++reg) 3016*e4b17023SJohn Marino if (TEST_HARD_REG_BIT (bi->out_reg_set, reg)) 3017*e4b17023SJohn Marino fprintf (dump_file, " %d", reg); 3018*e4b17023SJohn Marino fprintf (dump_file, " ]\nOutput stack: "); 3019*e4b17023SJohn Marino print_stack (dump_file, ®stack); 3020*e4b17023SJohn Marino } 3021*e4b17023SJohn Marino 3022*e4b17023SJohn Marino insn = BB_END (block); 3023*e4b17023SJohn Marino if (JUMP_P (insn)) 3024*e4b17023SJohn Marino insn = PREV_INSN (insn); 3025*e4b17023SJohn Marino 3026*e4b17023SJohn Marino /* If the function is declared to return a value, but it returns one 3027*e4b17023SJohn Marino in only some cases, some registers might come live here. Emit 3028*e4b17023SJohn Marino necessary moves for them. */ 3029*e4b17023SJohn Marino 3030*e4b17023SJohn Marino for (reg = FIRST_STACK_REG; reg <= LAST_STACK_REG; ++reg) 3031*e4b17023SJohn Marino { 3032*e4b17023SJohn Marino if (TEST_HARD_REG_BIT (bi->out_reg_set, reg) 3033*e4b17023SJohn Marino && ! TEST_HARD_REG_BIT (regstack.reg_set, reg)) 3034*e4b17023SJohn Marino { 3035*e4b17023SJohn Marino rtx set; 3036*e4b17023SJohn Marino 3037*e4b17023SJohn Marino if (dump_file) 3038*e4b17023SJohn Marino fprintf (dump_file, "Emitting insn initializing reg %d\n", reg); 3039*e4b17023SJohn Marino 3040*e4b17023SJohn Marino set = gen_rtx_SET (VOIDmode, FP_MODE_REG (reg, SFmode), not_a_num); 3041*e4b17023SJohn Marino insn = emit_insn_after (set, insn); 3042*e4b17023SJohn Marino control_flow_insn_deleted |= subst_stack_regs (insn, ®stack); 3043*e4b17023SJohn Marino } 3044*e4b17023SJohn Marino } 3045*e4b17023SJohn Marino 3046*e4b17023SJohn Marino /* Amongst the insns possibly deleted during the substitution process above, 3047*e4b17023SJohn Marino might have been the only trapping insn in the block. We purge the now 3048*e4b17023SJohn Marino possibly dead EH edges here to avoid an ICE from fixup_abnormal_edges, 3049*e4b17023SJohn Marino called at the end of convert_regs. The order in which we process the 3050*e4b17023SJohn Marino blocks ensures that we never delete an already processed edge. 3051*e4b17023SJohn Marino 3052*e4b17023SJohn Marino Note that, at this point, the CFG may have been damaged by the emission 3053*e4b17023SJohn Marino of instructions after an abnormal call, which moves the basic block end 3054*e4b17023SJohn Marino (and is the reason why we call fixup_abnormal_edges later). So we must 3055*e4b17023SJohn Marino be sure that the trapping insn has been deleted before trying to purge 3056*e4b17023SJohn Marino dead edges, otherwise we risk purging valid edges. 3057*e4b17023SJohn Marino 3058*e4b17023SJohn Marino ??? We are normally supposed not to delete trapping insns, so we pretend 3059*e4b17023SJohn Marino that the insns deleted above don't actually trap. It would have been 3060*e4b17023SJohn Marino better to detect this earlier and avoid creating the EH edge in the first 3061*e4b17023SJohn Marino place, still, but we don't have enough information at that time. */ 3062*e4b17023SJohn Marino 3063*e4b17023SJohn Marino if (control_flow_insn_deleted) 3064*e4b17023SJohn Marino cfg_altered |= purge_dead_edges (block); 3065*e4b17023SJohn Marino 3066*e4b17023SJohn Marino /* Something failed if the stack lives don't match. If we had malformed 3067*e4b17023SJohn Marino asms, we zapped the instruction itself, but that didn't produce the 3068*e4b17023SJohn Marino same pattern of register kills as before. */ 3069*e4b17023SJohn Marino 3070*e4b17023SJohn Marino gcc_assert (hard_reg_set_equal_p (regstack.reg_set, bi->out_reg_set) 3071*e4b17023SJohn Marino || any_malformed_asm); 3072*e4b17023SJohn Marino bi->stack_out = regstack; 3073*e4b17023SJohn Marino bi->done = true; 3074*e4b17023SJohn Marino 3075*e4b17023SJohn Marino return cfg_altered; 3076*e4b17023SJohn Marino } 3077*e4b17023SJohn Marino 3078*e4b17023SJohn Marino /* Convert registers in all blocks reachable from BLOCK. Return true if the 3079*e4b17023SJohn Marino CFG has been modified in the process. */ 3080*e4b17023SJohn Marino 3081*e4b17023SJohn Marino static bool 3082*e4b17023SJohn Marino convert_regs_2 (basic_block block) 3083*e4b17023SJohn Marino { 3084*e4b17023SJohn Marino basic_block *stack, *sp; 3085*e4b17023SJohn Marino bool cfg_altered = false; 3086*e4b17023SJohn Marino 3087*e4b17023SJohn Marino /* We process the blocks in a top-down manner, in a way such that one block 3088*e4b17023SJohn Marino is only processed after all its predecessors. The number of predecessors 3089*e4b17023SJohn Marino of every block has already been computed. */ 3090*e4b17023SJohn Marino 3091*e4b17023SJohn Marino stack = XNEWVEC (basic_block, n_basic_blocks); 3092*e4b17023SJohn Marino sp = stack; 3093*e4b17023SJohn Marino 3094*e4b17023SJohn Marino *sp++ = block; 3095*e4b17023SJohn Marino 3096*e4b17023SJohn Marino do 3097*e4b17023SJohn Marino { 3098*e4b17023SJohn Marino edge e; 3099*e4b17023SJohn Marino edge_iterator ei; 3100*e4b17023SJohn Marino 3101*e4b17023SJohn Marino block = *--sp; 3102*e4b17023SJohn Marino 3103*e4b17023SJohn Marino /* Processing BLOCK is achieved by convert_regs_1, which may purge 3104*e4b17023SJohn Marino some dead EH outgoing edge after the deletion of the trapping 3105*e4b17023SJohn Marino insn inside the block. Since the number of predecessors of 3106*e4b17023SJohn Marino BLOCK's successors was computed based on the initial edge set, 3107*e4b17023SJohn Marino we check the necessity to process some of these successors 3108*e4b17023SJohn Marino before such an edge deletion may happen. However, there is 3109*e4b17023SJohn Marino a pitfall: if BLOCK is the only predecessor of a successor and 3110*e4b17023SJohn Marino the edge between them happens to be deleted, the successor 3111*e4b17023SJohn Marino becomes unreachable and should not be processed. The problem 3112*e4b17023SJohn Marino is that there is no way to preventively detect this case so we 3113*e4b17023SJohn Marino stack the successor in all cases and hand over the task of 3114*e4b17023SJohn Marino fixing up the discrepancy to convert_regs_1. */ 3115*e4b17023SJohn Marino 3116*e4b17023SJohn Marino FOR_EACH_EDGE (e, ei, block->succs) 3117*e4b17023SJohn Marino if (! (e->flags & EDGE_DFS_BACK)) 3118*e4b17023SJohn Marino { 3119*e4b17023SJohn Marino BLOCK_INFO (e->dest)->predecessors--; 3120*e4b17023SJohn Marino if (!BLOCK_INFO (e->dest)->predecessors) 3121*e4b17023SJohn Marino *sp++ = e->dest; 3122*e4b17023SJohn Marino } 3123*e4b17023SJohn Marino 3124*e4b17023SJohn Marino cfg_altered |= convert_regs_1 (block); 3125*e4b17023SJohn Marino } 3126*e4b17023SJohn Marino while (sp != stack); 3127*e4b17023SJohn Marino 3128*e4b17023SJohn Marino free (stack); 3129*e4b17023SJohn Marino 3130*e4b17023SJohn Marino return cfg_altered; 3131*e4b17023SJohn Marino } 3132*e4b17023SJohn Marino 3133*e4b17023SJohn Marino /* Traverse all basic blocks in a function, converting the register 3134*e4b17023SJohn Marino references in each insn from the "flat" register file that gcc uses, 3135*e4b17023SJohn Marino to the stack-like registers the 387 uses. */ 3136*e4b17023SJohn Marino 3137*e4b17023SJohn Marino static void 3138*e4b17023SJohn Marino convert_regs (void) 3139*e4b17023SJohn Marino { 3140*e4b17023SJohn Marino bool cfg_altered = false; 3141*e4b17023SJohn Marino int inserted; 3142*e4b17023SJohn Marino basic_block b; 3143*e4b17023SJohn Marino edge e; 3144*e4b17023SJohn Marino edge_iterator ei; 3145*e4b17023SJohn Marino 3146*e4b17023SJohn Marino /* Initialize uninitialized registers on function entry. */ 3147*e4b17023SJohn Marino inserted = convert_regs_entry (); 3148*e4b17023SJohn Marino 3149*e4b17023SJohn Marino /* Construct the desired stack for function exit. */ 3150*e4b17023SJohn Marino convert_regs_exit (); 3151*e4b17023SJohn Marino BLOCK_INFO (EXIT_BLOCK_PTR)->done = 1; 3152*e4b17023SJohn Marino 3153*e4b17023SJohn Marino /* ??? Future: process inner loops first, and give them arbitrary 3154*e4b17023SJohn Marino initial stacks which emit_swap_insn can modify. This ought to 3155*e4b17023SJohn Marino prevent double fxch that often appears at the head of a loop. */ 3156*e4b17023SJohn Marino 3157*e4b17023SJohn Marino /* Process all blocks reachable from all entry points. */ 3158*e4b17023SJohn Marino FOR_EACH_EDGE (e, ei, ENTRY_BLOCK_PTR->succs) 3159*e4b17023SJohn Marino cfg_altered |= convert_regs_2 (e->dest); 3160*e4b17023SJohn Marino 3161*e4b17023SJohn Marino /* ??? Process all unreachable blocks. Though there's no excuse 3162*e4b17023SJohn Marino for keeping these even when not optimizing. */ 3163*e4b17023SJohn Marino FOR_EACH_BB (b) 3164*e4b17023SJohn Marino { 3165*e4b17023SJohn Marino block_info bi = BLOCK_INFO (b); 3166*e4b17023SJohn Marino 3167*e4b17023SJohn Marino if (! bi->done) 3168*e4b17023SJohn Marino cfg_altered |= convert_regs_2 (b); 3169*e4b17023SJohn Marino } 3170*e4b17023SJohn Marino 3171*e4b17023SJohn Marino /* We must fix up abnormal edges before inserting compensation code 3172*e4b17023SJohn Marino because both mechanisms insert insns on edges. */ 3173*e4b17023SJohn Marino inserted |= fixup_abnormal_edges (); 3174*e4b17023SJohn Marino 3175*e4b17023SJohn Marino inserted |= compensate_edges (); 3176*e4b17023SJohn Marino 3177*e4b17023SJohn Marino clear_aux_for_blocks (); 3178*e4b17023SJohn Marino 3179*e4b17023SJohn Marino if (inserted) 3180*e4b17023SJohn Marino commit_edge_insertions (); 3181*e4b17023SJohn Marino 3182*e4b17023SJohn Marino if (cfg_altered) 3183*e4b17023SJohn Marino cleanup_cfg (0); 3184*e4b17023SJohn Marino 3185*e4b17023SJohn Marino if (dump_file) 3186*e4b17023SJohn Marino fputc ('\n', dump_file); 3187*e4b17023SJohn Marino } 3188*e4b17023SJohn Marino 3189*e4b17023SJohn Marino /* Convert register usage from "flat" register file usage to a "stack 3190*e4b17023SJohn Marino register file. FILE is the dump file, if used. 3191*e4b17023SJohn Marino 3192*e4b17023SJohn Marino Construct a CFG and run life analysis. Then convert each insn one 3193*e4b17023SJohn Marino by one. Run a last cleanup_cfg pass, if optimizing, to eliminate 3194*e4b17023SJohn Marino code duplication created when the converter inserts pop insns on 3195*e4b17023SJohn Marino the edges. */ 3196*e4b17023SJohn Marino 3197*e4b17023SJohn Marino static bool 3198*e4b17023SJohn Marino reg_to_stack (void) 3199*e4b17023SJohn Marino { 3200*e4b17023SJohn Marino basic_block bb; 3201*e4b17023SJohn Marino int i; 3202*e4b17023SJohn Marino int max_uid; 3203*e4b17023SJohn Marino 3204*e4b17023SJohn Marino /* Clean up previous run. */ 3205*e4b17023SJohn Marino if (stack_regs_mentioned_data != NULL) 3206*e4b17023SJohn Marino VEC_free (char, heap, stack_regs_mentioned_data); 3207*e4b17023SJohn Marino 3208*e4b17023SJohn Marino /* See if there is something to do. Flow analysis is quite 3209*e4b17023SJohn Marino expensive so we might save some compilation time. */ 3210*e4b17023SJohn Marino for (i = FIRST_STACK_REG; i <= LAST_STACK_REG; i++) 3211*e4b17023SJohn Marino if (df_regs_ever_live_p (i)) 3212*e4b17023SJohn Marino break; 3213*e4b17023SJohn Marino if (i > LAST_STACK_REG) 3214*e4b17023SJohn Marino return false; 3215*e4b17023SJohn Marino 3216*e4b17023SJohn Marino df_note_add_problem (); 3217*e4b17023SJohn Marino df_analyze (); 3218*e4b17023SJohn Marino 3219*e4b17023SJohn Marino mark_dfs_back_edges (); 3220*e4b17023SJohn Marino 3221*e4b17023SJohn Marino /* Set up block info for each basic block. */ 3222*e4b17023SJohn Marino alloc_aux_for_blocks (sizeof (struct block_info_def)); 3223*e4b17023SJohn Marino FOR_EACH_BB (bb) 3224*e4b17023SJohn Marino { 3225*e4b17023SJohn Marino block_info bi = BLOCK_INFO (bb); 3226*e4b17023SJohn Marino edge_iterator ei; 3227*e4b17023SJohn Marino edge e; 3228*e4b17023SJohn Marino int reg; 3229*e4b17023SJohn Marino 3230*e4b17023SJohn Marino FOR_EACH_EDGE (e, ei, bb->preds) 3231*e4b17023SJohn Marino if (!(e->flags & EDGE_DFS_BACK) 3232*e4b17023SJohn Marino && e->src != ENTRY_BLOCK_PTR) 3233*e4b17023SJohn Marino bi->predecessors++; 3234*e4b17023SJohn Marino 3235*e4b17023SJohn Marino /* Set current register status at last instruction `uninitialized'. */ 3236*e4b17023SJohn Marino bi->stack_in.top = -2; 3237*e4b17023SJohn Marino 3238*e4b17023SJohn Marino /* Copy live_at_end and live_at_start into temporaries. */ 3239*e4b17023SJohn Marino for (reg = FIRST_STACK_REG; reg <= LAST_STACK_REG; reg++) 3240*e4b17023SJohn Marino { 3241*e4b17023SJohn Marino if (REGNO_REG_SET_P (DF_LR_OUT (bb), reg)) 3242*e4b17023SJohn Marino SET_HARD_REG_BIT (bi->out_reg_set, reg); 3243*e4b17023SJohn Marino if (REGNO_REG_SET_P (DF_LR_IN (bb), reg)) 3244*e4b17023SJohn Marino SET_HARD_REG_BIT (bi->stack_in.reg_set, reg); 3245*e4b17023SJohn Marino } 3246*e4b17023SJohn Marino } 3247*e4b17023SJohn Marino 3248*e4b17023SJohn Marino /* Create the replacement registers up front. */ 3249*e4b17023SJohn Marino for (i = FIRST_STACK_REG; i <= LAST_STACK_REG; i++) 3250*e4b17023SJohn Marino { 3251*e4b17023SJohn Marino enum machine_mode mode; 3252*e4b17023SJohn Marino for (mode = GET_CLASS_NARROWEST_MODE (MODE_FLOAT); 3253*e4b17023SJohn Marino mode != VOIDmode; 3254*e4b17023SJohn Marino mode = GET_MODE_WIDER_MODE (mode)) 3255*e4b17023SJohn Marino FP_MODE_REG (i, mode) = gen_rtx_REG (mode, i); 3256*e4b17023SJohn Marino for (mode = GET_CLASS_NARROWEST_MODE (MODE_COMPLEX_FLOAT); 3257*e4b17023SJohn Marino mode != VOIDmode; 3258*e4b17023SJohn Marino mode = GET_MODE_WIDER_MODE (mode)) 3259*e4b17023SJohn Marino FP_MODE_REG (i, mode) = gen_rtx_REG (mode, i); 3260*e4b17023SJohn Marino } 3261*e4b17023SJohn Marino 3262*e4b17023SJohn Marino ix86_flags_rtx = gen_rtx_REG (CCmode, FLAGS_REG); 3263*e4b17023SJohn Marino 3264*e4b17023SJohn Marino /* A QNaN for initializing uninitialized variables. 3265*e4b17023SJohn Marino 3266*e4b17023SJohn Marino ??? We can't load from constant memory in PIC mode, because 3267*e4b17023SJohn Marino we're inserting these instructions before the prologue and 3268*e4b17023SJohn Marino the PIC register hasn't been set up. In that case, fall back 3269*e4b17023SJohn Marino on zero, which we can get from `fldz'. */ 3270*e4b17023SJohn Marino 3271*e4b17023SJohn Marino if ((flag_pic && !TARGET_64BIT) 3272*e4b17023SJohn Marino || ix86_cmodel == CM_LARGE || ix86_cmodel == CM_LARGE_PIC) 3273*e4b17023SJohn Marino not_a_num = CONST0_RTX (SFmode); 3274*e4b17023SJohn Marino else 3275*e4b17023SJohn Marino { 3276*e4b17023SJohn Marino REAL_VALUE_TYPE r; 3277*e4b17023SJohn Marino 3278*e4b17023SJohn Marino real_nan (&r, "", 1, SFmode); 3279*e4b17023SJohn Marino not_a_num = CONST_DOUBLE_FROM_REAL_VALUE (r, SFmode); 3280*e4b17023SJohn Marino not_a_num = force_const_mem (SFmode, not_a_num); 3281*e4b17023SJohn Marino } 3282*e4b17023SJohn Marino 3283*e4b17023SJohn Marino /* Allocate a cache for stack_regs_mentioned. */ 3284*e4b17023SJohn Marino max_uid = get_max_uid (); 3285*e4b17023SJohn Marino stack_regs_mentioned_data = VEC_alloc (char, heap, max_uid + 1); 3286*e4b17023SJohn Marino memset (VEC_address (char, stack_regs_mentioned_data), 3287*e4b17023SJohn Marino 0, sizeof (char) * (max_uid + 1)); 3288*e4b17023SJohn Marino 3289*e4b17023SJohn Marino convert_regs (); 3290*e4b17023SJohn Marino 3291*e4b17023SJohn Marino free_aux_for_blocks (); 3292*e4b17023SJohn Marino return true; 3293*e4b17023SJohn Marino } 3294*e4b17023SJohn Marino #endif /* STACK_REGS */ 3295*e4b17023SJohn Marino 3296*e4b17023SJohn Marino static bool 3297*e4b17023SJohn Marino gate_handle_stack_regs (void) 3298*e4b17023SJohn Marino { 3299*e4b17023SJohn Marino #ifdef STACK_REGS 3300*e4b17023SJohn Marino return 1; 3301*e4b17023SJohn Marino #else 3302*e4b17023SJohn Marino return 0; 3303*e4b17023SJohn Marino #endif 3304*e4b17023SJohn Marino } 3305*e4b17023SJohn Marino 3306*e4b17023SJohn Marino struct rtl_opt_pass pass_stack_regs = 3307*e4b17023SJohn Marino { 3308*e4b17023SJohn Marino { 3309*e4b17023SJohn Marino RTL_PASS, 3310*e4b17023SJohn Marino "*stack_regs", /* name */ 3311*e4b17023SJohn Marino gate_handle_stack_regs, /* gate */ 3312*e4b17023SJohn Marino NULL, /* execute */ 3313*e4b17023SJohn Marino NULL, /* sub */ 3314*e4b17023SJohn Marino NULL, /* next */ 3315*e4b17023SJohn Marino 0, /* static_pass_number */ 3316*e4b17023SJohn Marino TV_REG_STACK, /* tv_id */ 3317*e4b17023SJohn Marino 0, /* properties_required */ 3318*e4b17023SJohn Marino 0, /* properties_provided */ 3319*e4b17023SJohn Marino 0, /* properties_destroyed */ 3320*e4b17023SJohn Marino 0, /* todo_flags_start */ 3321*e4b17023SJohn Marino 0 /* todo_flags_finish */ 3322*e4b17023SJohn Marino } 3323*e4b17023SJohn Marino }; 3324*e4b17023SJohn Marino 3325*e4b17023SJohn Marino /* Convert register usage from flat register file usage to a stack 3326*e4b17023SJohn Marino register file. */ 3327*e4b17023SJohn Marino static unsigned int 3328*e4b17023SJohn Marino rest_of_handle_stack_regs (void) 3329*e4b17023SJohn Marino { 3330*e4b17023SJohn Marino #ifdef STACK_REGS 3331*e4b17023SJohn Marino reg_to_stack (); 3332*e4b17023SJohn Marino regstack_completed = 1; 3333*e4b17023SJohn Marino #endif 3334*e4b17023SJohn Marino return 0; 3335*e4b17023SJohn Marino } 3336*e4b17023SJohn Marino 3337*e4b17023SJohn Marino struct rtl_opt_pass pass_stack_regs_run = 3338*e4b17023SJohn Marino { 3339*e4b17023SJohn Marino { 3340*e4b17023SJohn Marino RTL_PASS, 3341*e4b17023SJohn Marino "stack", /* name */ 3342*e4b17023SJohn Marino NULL, /* gate */ 3343*e4b17023SJohn Marino rest_of_handle_stack_regs, /* execute */ 3344*e4b17023SJohn Marino NULL, /* sub */ 3345*e4b17023SJohn Marino NULL, /* next */ 3346*e4b17023SJohn Marino 0, /* static_pass_number */ 3347*e4b17023SJohn Marino TV_REG_STACK, /* tv_id */ 3348*e4b17023SJohn Marino 0, /* properties_required */ 3349*e4b17023SJohn Marino 0, /* properties_provided */ 3350*e4b17023SJohn Marino 0, /* properties_destroyed */ 3351*e4b17023SJohn Marino 0, /* todo_flags_start */ 3352*e4b17023SJohn Marino TODO_df_finish | TODO_verify_rtl_sharing | 3353*e4b17023SJohn Marino TODO_ggc_collect /* todo_flags_finish */ 3354*e4b17023SJohn Marino } 3355*e4b17023SJohn Marino }; 3356