118334Speter/* Register to Stack convert for GNU compiler. 2132718Skan Copyright (C) 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999, 3169689Skan 2000, 2001, 2002, 2003, 2004, 2005 Free Software Foundation, Inc. 418334Speter 590075Sobrien This file is part of GCC. 618334Speter 790075Sobrien GCC is free software; you can redistribute it and/or modify it 890075Sobrien under the terms of the GNU General Public License as published by 990075Sobrien the Free Software Foundation; either version 2, or (at your option) 1090075Sobrien any later version. 1118334Speter 1290075Sobrien GCC is distributed in the hope that it will be useful, but WITHOUT 1390075Sobrien ANY WARRANTY; without even the implied warranty of MERCHANTABILITY 1490075Sobrien or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public 1590075Sobrien License for more details. 1618334Speter 1790075Sobrien You should have received a copy of the GNU General Public License 1890075Sobrien along with GCC; see the file COPYING. If not, write to the Free 19169689Skan Software Foundation, 51 Franklin Street, Fifth Floor, Boston, MA 20169689Skan 02110-1301, USA. */ 2118334Speter 2218334Speter/* This pass converts stack-like registers from the "flat register 2318334Speter file" model that gcc uses, to a stack convention that the 387 uses. 2418334Speter 2518334Speter * The form of the input: 2618334Speter 2718334Speter On input, the function consists of insn that have had their 2818334Speter registers fully allocated to a set of "virtual" registers. Note that 2918334Speter the word "virtual" is used differently here than elsewhere in gcc: for 3018334Speter each virtual stack reg, there is a hard reg, but the mapping between 3118334Speter them is not known until this pass is run. On output, hard register 3218334Speter numbers have been substituted, and various pop and exchange insns have 3318334Speter been emitted. The hard register numbers and the virtual register 3418334Speter numbers completely overlap - before this pass, all stack register 3518334Speter numbers are virtual, and afterward they are all hard. 3618334Speter 3718334Speter The virtual registers can be manipulated normally by gcc, and their 3818334Speter semantics are the same as for normal registers. After the hard 3918334Speter register numbers are substituted, the semantics of an insn containing 4018334Speter stack-like regs are not the same as for an insn with normal regs: for 4118334Speter instance, it is not safe to delete an insn that appears to be a no-op 4218334Speter move. In general, no insn containing hard regs should be changed 4318334Speter after this pass is done. 4418334Speter 4518334Speter * The form of the output: 4618334Speter 4718334Speter After this pass, hard register numbers represent the distance from 4818334Speter the current top of stack to the desired register. A reference to 4918334Speter FIRST_STACK_REG references the top of stack, FIRST_STACK_REG + 1, 5018334Speter represents the register just below that, and so forth. Also, REG_DEAD 5118334Speter notes indicate whether or not a stack register should be popped. 5218334Speter 5318334Speter A "swap" insn looks like a parallel of two patterns, where each 5418334Speter pattern is a SET: one sets A to B, the other B to A. 5518334Speter 5618334Speter A "push" or "load" insn is a SET whose SET_DEST is FIRST_STACK_REG 5718334Speter and whose SET_DEST is REG or MEM. Any other SET_DEST, such as PLUS, 5818334Speter will replace the existing stack top, not push a new value. 5918334Speter 6018334Speter A store insn is a SET whose SET_DEST is FIRST_STACK_REG, and whose 6118334Speter SET_SRC is REG or MEM. 6218334Speter 6318334Speter The case where the SET_SRC and SET_DEST are both FIRST_STACK_REG 6418334Speter appears ambiguous. As a special case, the presence of a REG_DEAD note 6518334Speter for FIRST_STACK_REG differentiates between a load insn and a pop. 6618334Speter 6718334Speter If a REG_DEAD is present, the insn represents a "pop" that discards 6818334Speter the top of the register stack. If there is no REG_DEAD note, then the 6918334Speter insn represents a "dup" or a push of the current top of stack onto the 7018334Speter stack. 7118334Speter 7218334Speter * Methodology: 7318334Speter 7418334Speter Existing REG_DEAD and REG_UNUSED notes for stack registers are 7518334Speter deleted and recreated from scratch. REG_DEAD is never created for a 7618334Speter SET_DEST, only REG_UNUSED. 7718334Speter 7818334Speter * asm_operands: 7918334Speter 8018334Speter There are several rules on the usage of stack-like regs in 8118334Speter asm_operands insns. These rules apply only to the operands that are 8218334Speter stack-like regs: 8318334Speter 8418334Speter 1. Given a set of input regs that die in an asm_operands, it is 8518334Speter necessary to know which are implicitly popped by the asm, and 8618334Speter which must be explicitly popped by gcc. 8718334Speter 8818334Speter An input reg that is implicitly popped by the asm must be 8918334Speter explicitly clobbered, unless it is constrained to match an 9018334Speter output operand. 9118334Speter 9218334Speter 2. For any input reg that is implicitly popped by an asm, it is 9318334Speter necessary to know how to adjust the stack to compensate for the pop. 9418334Speter If any non-popped input is closer to the top of the reg-stack than 9518334Speter the implicitly popped reg, it would not be possible to know what the 9618334Speter stack looked like - it's not clear how the rest of the stack "slides 9718334Speter up". 9818334Speter 9918334Speter All implicitly popped input regs must be closer to the top of 10018334Speter the reg-stack than any input that is not implicitly popped. 10118334Speter 10218334Speter 3. It is possible that if an input dies in an insn, reload might 10318334Speter use the input reg for an output reload. Consider this example: 10418334Speter 10518334Speter asm ("foo" : "=t" (a) : "f" (b)); 10618334Speter 10718334Speter This asm says that input B is not popped by the asm, and that 108169689Skan the asm pushes a result onto the reg-stack, i.e., the stack is one 10918334Speter deeper after the asm than it was before. But, it is possible that 11018334Speter reload will think that it can use the same reg for both the input and 11118334Speter the output, if input B dies in this insn. 11218334Speter 11318334Speter If any input operand uses the "f" constraint, all output reg 11418334Speter constraints must use the "&" earlyclobber. 11518334Speter 11618334Speter The asm above would be written as 11718334Speter 11818334Speter asm ("foo" : "=&t" (a) : "f" (b)); 11918334Speter 12018334Speter 4. Some operands need to be in particular places on the stack. All 12118334Speter output operands fall in this category - there is no other way to 12218334Speter know which regs the outputs appear in unless the user indicates 12318334Speter this in the constraints. 12418334Speter 12518334Speter Output operands must specifically indicate which reg an output 12618334Speter appears in after an asm. "=f" is not allowed: the operand 12718334Speter constraints must select a class with a single reg. 12818334Speter 12918334Speter 5. Output operands may not be "inserted" between existing stack regs. 13018334Speter Since no 387 opcode uses a read/write operand, all output operands 13118334Speter are dead before the asm_operands, and are pushed by the asm_operands. 13218334Speter It makes no sense to push anywhere but the top of the reg-stack. 13318334Speter 13418334Speter Output operands must start at the top of the reg-stack: output 13518334Speter operands may not "skip" a reg. 13618334Speter 13718334Speter 6. Some asm statements may need extra stack space for internal 13818334Speter calculations. This can be guaranteed by clobbering stack registers 13918334Speter unrelated to the inputs and outputs. 14018334Speter 14118334Speter Here are a couple of reasonable asms to want to write. This asm 14218334Speter takes one input, which is internally popped, and produces two outputs. 14318334Speter 14418334Speter asm ("fsincos" : "=t" (cos), "=u" (sin) : "0" (inp)); 14518334Speter 14618334Speter This asm takes two inputs, which are popped by the fyl2xp1 opcode, 14718334Speter and replaces them with one output. The user must code the "st(1)" 14818334Speter clobber for reg-stack.c to know that fyl2xp1 pops both inputs. 14918334Speter 15018334Speter asm ("fyl2xp1" : "=t" (result) : "0" (x), "u" (y) : "st(1)"); 15118334Speter 15290075Sobrien*/ 15318334Speter 15418334Speter#include "config.h" 15550397Sobrien#include "system.h" 156132718Skan#include "coretypes.h" 157132718Skan#include "tm.h" 15818334Speter#include "tree.h" 15918334Speter#include "rtl.h" 16090075Sobrien#include "tm_p.h" 16190075Sobrien#include "function.h" 16218334Speter#include "insn-config.h" 16318334Speter#include "regs.h" 16418334Speter#include "hard-reg-set.h" 16518334Speter#include "flags.h" 16690075Sobrien#include "toplev.h" 16752284Sobrien#include "recog.h" 16890075Sobrien#include "output.h" 16990075Sobrien#include "basic-block.h" 17052284Sobrien#include "varray.h" 17190075Sobrien#include "reload.h" 172117395Skan#include "ggc.h" 173169689Skan#include "timevar.h" 174169689Skan#include "tree-pass.h" 175169689Skan#include "target.h" 176169689Skan#include "vecprim.h" 17718334Speter 178169689Skan#ifdef STACK_REGS 179169689Skan 180117395Skan/* We use this array to cache info about insns, because otherwise we 181117395Skan spend too much time in stack_regs_mentioned_p. 182117395Skan 183117395Skan Indexed by insn UIDs. A value of zero is uninitialized, one indicates 184117395Skan the insn uses stack registers, two indicates the insn does not use 185117395Skan stack registers. */ 186169689Skanstatic VEC(char,heap) *stack_regs_mentioned_data; 187117395Skan 18818334Speter#define REG_STACK_SIZE (LAST_STACK_REG - FIRST_STACK_REG + 1) 18918334Speter 190169689Skanint regstack_completed = 0; 191169689Skan 19218334Speter/* This is the basic stack record. TOP is an index into REG[] such 19318334Speter that REG[TOP] is the top of stack. If TOP is -1 the stack is empty. 19418334Speter 19518334Speter If TOP is -2, REG[] is not yet initialized. Stack initialization 19618334Speter consists of placing each live reg in array `reg' and setting `top' 19718334Speter appropriately. 19818334Speter 19918334Speter REG_SET indicates which registers are live. */ 20018334Speter 20118334Spetertypedef struct stack_def 20218334Speter{ 20318334Speter int top; /* index to top stack element */ 20418334Speter HARD_REG_SET reg_set; /* set of live registers */ 20590075Sobrien unsigned char reg[REG_STACK_SIZE];/* register - stack mapping */ 20618334Speter} *stack; 20718334Speter 208117395Skan/* This is used to carry information about basic blocks. It is 20990075Sobrien attached to the AUX field of the standard CFG block. */ 21018334Speter 21190075Sobrientypedef struct block_info_def 21290075Sobrien{ 21390075Sobrien struct stack_def stack_in; /* Input stack configuration. */ 21490075Sobrien struct stack_def stack_out; /* Output stack configuration. */ 21590075Sobrien HARD_REG_SET out_reg_set; /* Stack regs live on output. */ 21690075Sobrien int done; /* True if block already converted. */ 217169689Skan int predecessors; /* Number of predecessors that need 21890075Sobrien to be visited. */ 21990075Sobrien} *block_info; 22018334Speter 22190075Sobrien#define BLOCK_INFO(B) ((block_info) (B)->aux) 22218334Speter 22390075Sobrien/* Passed to change_stack to indicate where to emit insns. */ 22490075Sobrienenum emit_where 22590075Sobrien{ 22690075Sobrien EMIT_AFTER, 22790075Sobrien EMIT_BEFORE 22890075Sobrien}; 22918334Speter 23090075Sobrien/* The block we're currently working on. */ 23190075Sobrienstatic basic_block current_block; 23290075Sobrien 233169689Skan/* In the current_block, whether we're processing the first register 234169689Skan stack or call instruction, i.e. the regstack is currently the 235169689Skan same as BLOCK_INFO(current_block)->stack_in. */ 236169689Skanstatic bool starting_stack_p; 237169689Skan 238117395Skan/* This is the register file for all register after conversion. */ 23918334Speterstatic rtx 24018334Speter FP_mode_reg[LAST_STACK_REG+1-FIRST_STACK_REG][(int) MAX_MACHINE_MODE]; 24118334Speter 24218334Speter#define FP_MODE_REG(regno,mode) \ 24390075Sobrien (FP_mode_reg[(regno)-FIRST_STACK_REG][(int) (mode)]) 24418334Speter 24590075Sobrien/* Used to initialize uninitialized registers. */ 246169689Skanstatic rtx not_a_num; 24718334Speter 24818334Speter/* Forward declarations */ 24918334Speter 250132718Skanstatic int stack_regs_mentioned_p (rtx pat); 251132718Skanstatic void pop_stack (stack, int); 252132718Skanstatic rtx *get_true_reg (rtx *); 25350397Sobrien 254132718Skanstatic int check_asm_stack_operands (rtx); 255132718Skanstatic int get_asm_operand_n_inputs (rtx); 256132718Skanstatic rtx stack_result (tree); 257132718Skanstatic void replace_reg (rtx *, int); 258132718Skanstatic void remove_regno_note (rtx, enum reg_note, unsigned int); 259132718Skanstatic int get_hard_regnum (stack, rtx); 260132718Skanstatic rtx emit_pop_insn (rtx, stack, rtx, enum emit_where); 261169689Skanstatic void swap_to_top(rtx, stack, rtx, rtx); 262132718Skanstatic bool move_for_stack_reg (rtx, stack, rtx); 263169689Skanstatic bool move_nan_for_stack_reg (rtx, stack, rtx); 264132718Skanstatic int swap_rtx_condition_1 (rtx); 265132718Skanstatic int swap_rtx_condition (rtx); 266132718Skanstatic void compare_for_stack_reg (rtx, stack, rtx); 267132718Skanstatic bool subst_stack_regs_pat (rtx, stack, rtx); 268132718Skanstatic void subst_asm_stack_regs (rtx, stack); 269132718Skanstatic bool subst_stack_regs (rtx, stack); 270132718Skanstatic void change_stack (rtx, stack, stack, enum emit_where); 271132718Skanstatic void print_stack (FILE *, stack); 272132718Skanstatic rtx next_flags_user (rtx); 27318334Speter 274117395Skan/* Return nonzero if any stack register is mentioned somewhere within PAT. */ 27552284Sobrien 27652284Sobrienstatic int 277132718Skanstack_regs_mentioned_p (rtx pat) 27852284Sobrien{ 27990075Sobrien const char *fmt; 28090075Sobrien int i; 28190075Sobrien 28290075Sobrien if (STACK_REG_P (pat)) 28390075Sobrien return 1; 28490075Sobrien 28590075Sobrien fmt = GET_RTX_FORMAT (GET_CODE (pat)); 28690075Sobrien for (i = GET_RTX_LENGTH (GET_CODE (pat)) - 1; i >= 0; i--) 28752284Sobrien { 28890075Sobrien if (fmt[i] == 'E') 28990075Sobrien { 29090075Sobrien int j; 29190075Sobrien 29290075Sobrien for (j = XVECLEN (pat, i) - 1; j >= 0; j--) 29390075Sobrien if (stack_regs_mentioned_p (XVECEXP (pat, i, j))) 29490075Sobrien return 1; 29590075Sobrien } 29690075Sobrien else if (fmt[i] == 'e' && stack_regs_mentioned_p (XEXP (pat, i))) 29790075Sobrien return 1; 29852284Sobrien } 29990075Sobrien 30052284Sobrien return 0; 30152284Sobrien} 30252284Sobrien 30390075Sobrien/* Return nonzero if INSN mentions stacked registers, else return zero. */ 30452284Sobrien 30552284Sobrienint 306132718Skanstack_regs_mentioned (rtx insn) 30752284Sobrien{ 30890075Sobrien unsigned int uid, max; 30990075Sobrien int test; 31090075Sobrien 31190075Sobrien if (! INSN_P (insn) || !stack_regs_mentioned_data) 31252284Sobrien return 0; 31390075Sobrien 31452284Sobrien uid = INSN_UID (insn); 315169689Skan max = VEC_length (char, stack_regs_mentioned_data); 31690075Sobrien if (uid >= max) 31790075Sobrien { 318169689Skan char *p; 319169689Skan unsigned int old_max = max; 320169689Skan 32190075Sobrien /* Allocate some extra size to avoid too many reallocs, but 32290075Sobrien do not grow too quickly. */ 323169689Skan max = uid + uid / 20 + 1; 324169689Skan VEC_safe_grow (char, heap, stack_regs_mentioned_data, max); 325169689Skan p = VEC_address (char, stack_regs_mentioned_data); 326169689Skan memset (&p[old_max], 0, 327169689Skan sizeof (char) * (max - old_max)); 32890075Sobrien } 32990075Sobrien 330169689Skan test = VEC_index (char, stack_regs_mentioned_data, uid); 33190075Sobrien if (test == 0) 33290075Sobrien { 33390075Sobrien /* This insn has yet to be examined. Do so now. */ 33490075Sobrien test = stack_regs_mentioned_p (PATTERN (insn)) ? 1 : 2; 335169689Skan VEC_replace (char, stack_regs_mentioned_data, uid, test); 33690075Sobrien } 33790075Sobrien 33890075Sobrien return test == 1; 33952284Sobrien} 34052284Sobrien 34190075Sobrienstatic rtx ix86_flags_rtx; 34218334Speter 34390075Sobrienstatic rtx 344132718Skannext_flags_user (rtx insn) 34518334Speter{ 346117395Skan /* Search forward looking for the first use of this value. 34790075Sobrien Stop at block boundaries. */ 34818334Speter 349132718Skan while (insn != BB_END (current_block)) 35090075Sobrien { 35190075Sobrien insn = NEXT_INSN (insn); 35218334Speter 35390075Sobrien if (INSN_P (insn) && reg_mentioned_p (ix86_flags_rtx, PATTERN (insn))) 354117395Skan return insn; 35590075Sobrien 356169689Skan if (CALL_P (insn)) 35790075Sobrien return NULL_RTX; 35890075Sobrien } 35990075Sobrien return NULL_RTX; 36018334Speter} 36118334Speter 362169689Skan/* Reorganize the stack into ascending numbers, before this insn. */ 36318334Speter 36418334Speterstatic void 365132718Skanstraighten_stack (rtx insn, stack regstack) 36618334Speter{ 36718334Speter struct stack_def temp_stack; 36818334Speter int top; 36918334Speter 37050397Sobrien /* If there is only a single register on the stack, then the stack is 37150397Sobrien already in increasing order and no reorganization is needed. 37250397Sobrien 37350397Sobrien Similarly if the stack is empty. */ 37450397Sobrien if (regstack->top <= 0) 37550397Sobrien return; 37650397Sobrien 37790075Sobrien COPY_HARD_REG_SET (temp_stack.reg_set, regstack->reg_set); 37818334Speter 37918334Speter for (top = temp_stack.top = regstack->top; top >= 0; top--) 38090075Sobrien temp_stack.reg[top] = FIRST_STACK_REG + temp_stack.top - top; 381117395Skan 382169689Skan change_stack (insn, regstack, &temp_stack, EMIT_BEFORE); 38318334Speter} 38450397Sobrien 385117395Skan/* Pop a register from the stack. */ 38650397Sobrien 38750397Sobrienstatic void 388132718Skanpop_stack (stack regstack, int regno) 38950397Sobrien{ 39050397Sobrien int top = regstack->top; 39150397Sobrien 39250397Sobrien CLEAR_HARD_REG_BIT (regstack->reg_set, regno); 39350397Sobrien regstack->top--; 394117395Skan /* If regno was not at the top of stack then adjust stack. */ 39550397Sobrien if (regstack->reg [top] != regno) 39650397Sobrien { 39750397Sobrien int i; 39850397Sobrien for (i = regstack->top; i >= 0; i--) 39950397Sobrien if (regstack->reg [i] == regno) 40050397Sobrien { 40150397Sobrien int j; 40250397Sobrien for (j = i; j < top; j++) 40350397Sobrien regstack->reg [j] = regstack->reg [j + 1]; 40450397Sobrien break; 40550397Sobrien } 40650397Sobrien } 40750397Sobrien} 40818334Speter 40918334Speter/* Return a pointer to the REG expression within PAT. If PAT is not a 41018334Speter REG, possible enclosed by a conversion rtx, return the inner part of 41150397Sobrien PAT that stopped the search. */ 41218334Speter 41318334Speterstatic rtx * 414132718Skanget_true_reg (rtx *pat) 41518334Speter{ 41618334Speter for (;;) 41790075Sobrien switch (GET_CODE (*pat)) 41818334Speter { 41990075Sobrien case SUBREG: 420117395Skan /* Eliminate FP subregister accesses in favor of the 42190075Sobrien actual FP register in use. */ 42290075Sobrien { 42390075Sobrien rtx subreg; 42490075Sobrien if (FP_REG_P (subreg = SUBREG_REG (*pat))) 42518334Speter { 42690075Sobrien int regno_off = subreg_regno_offset (REGNO (subreg), 42790075Sobrien GET_MODE (subreg), 42890075Sobrien SUBREG_BYTE (*pat), 42990075Sobrien GET_MODE (*pat)); 43090075Sobrien *pat = FP_MODE_REG (REGNO (subreg) + regno_off, 43118334Speter GET_MODE (subreg)); 43290075Sobrien default: 43318334Speter return pat; 43418334Speter } 43590075Sobrien } 43690075Sobrien case FLOAT: 43790075Sobrien case FIX: 43890075Sobrien case FLOAT_EXTEND: 43990075Sobrien pat = & XEXP (*pat, 0); 440169689Skan break; 441169689Skan 442169689Skan case FLOAT_TRUNCATE: 443169689Skan if (!flag_unsafe_math_optimizations) 444169689Skan return pat; 445169689Skan pat = & XEXP (*pat, 0); 446169689Skan break; 44718334Speter } 44818334Speter} 44918334Speter 450117395Skan/* Set if we find any malformed asms in a block. */ 451117395Skanstatic bool any_malformed_asm; 452117395Skan 45390075Sobrien/* There are many rules that an asm statement for stack-like regs must 45418334Speter follow. Those rules are explained at the top of this file: the rule 45550397Sobrien numbers below refer to that explanation. */ 45618334Speter 45790075Sobrienstatic int 458132718Skancheck_asm_stack_operands (rtx insn) 45918334Speter{ 46018334Speter int i; 46118334Speter int n_clobbers; 46218334Speter int malformed_asm = 0; 46318334Speter rtx body = PATTERN (insn); 46418334Speter 46590075Sobrien char reg_used_as_output[FIRST_PSEUDO_REGISTER]; 46690075Sobrien char implicitly_dies[FIRST_PSEUDO_REGISTER]; 46752284Sobrien int alt; 46818334Speter 46990075Sobrien rtx *clobber_reg = 0; 47052284Sobrien int n_inputs, n_outputs; 47118334Speter 47218334Speter /* Find out what the constraints require. If no constraint 47318334Speter alternative matches, this asm is malformed. */ 47452284Sobrien extract_insn (insn); 47552284Sobrien constrain_operands (1); 47652284Sobrien alt = which_alternative; 47718334Speter 47852284Sobrien preprocess_constraints (); 47952284Sobrien 48052284Sobrien n_inputs = get_asm_operand_n_inputs (body); 48190075Sobrien n_outputs = recog_data.n_operands - n_inputs; 48252284Sobrien 48352284Sobrien if (alt < 0) 48452284Sobrien { 48552284Sobrien malformed_asm = 1; 48652284Sobrien /* Avoid further trouble with this insn. */ 48752284Sobrien PATTERN (insn) = gen_rtx_USE (VOIDmode, const0_rtx); 48890075Sobrien return 0; 48952284Sobrien } 49052284Sobrien 49150397Sobrien /* Strip SUBREGs here to make the following code simpler. */ 49290075Sobrien for (i = 0; i < recog_data.n_operands; i++) 49390075Sobrien if (GET_CODE (recog_data.operand[i]) == SUBREG 494169689Skan && REG_P (SUBREG_REG (recog_data.operand[i]))) 49590075Sobrien recog_data.operand[i] = SUBREG_REG (recog_data.operand[i]); 49618334Speter 49718334Speter /* Set up CLOBBER_REG. */ 49818334Speter 49918334Speter n_clobbers = 0; 50018334Speter 50118334Speter if (GET_CODE (body) == PARALLEL) 50218334Speter { 503132718Skan clobber_reg = alloca (XVECLEN (body, 0) * sizeof (rtx)); 50418334Speter 50518334Speter for (i = 0; i < XVECLEN (body, 0); i++) 50618334Speter if (GET_CODE (XVECEXP (body, 0, i)) == CLOBBER) 50718334Speter { 50818334Speter rtx clobber = XVECEXP (body, 0, i); 50918334Speter rtx reg = XEXP (clobber, 0); 51018334Speter 511169689Skan if (GET_CODE (reg) == SUBREG && REG_P (SUBREG_REG (reg))) 51218334Speter reg = SUBREG_REG (reg); 51318334Speter 51418334Speter if (STACK_REG_P (reg)) 51518334Speter { 51618334Speter clobber_reg[n_clobbers] = reg; 51718334Speter n_clobbers++; 51818334Speter } 51918334Speter } 52018334Speter } 52118334Speter 52218334Speter /* Enforce rule #4: Output operands must specifically indicate which 52318334Speter reg an output appears in after an asm. "=f" is not allowed: the 52418334Speter operand constraints must select a class with a single reg. 52518334Speter 52618334Speter Also enforce rule #5: Output operands must start at the top of 52750397Sobrien the reg-stack: output operands may not "skip" a reg. */ 52818334Speter 52990075Sobrien memset (reg_used_as_output, 0, sizeof (reg_used_as_output)); 53018334Speter for (i = 0; i < n_outputs; i++) 53190075Sobrien if (STACK_REG_P (recog_data.operand[i])) 53250397Sobrien { 533169689Skan if (reg_class_size[(int) recog_op_alt[i][alt].cl] != 1) 53450397Sobrien { 53590075Sobrien error_for_asm (insn, "output constraint %d must specify a single register", i); 53650397Sobrien malformed_asm = 1; 53750397Sobrien } 538117395Skan else 53990075Sobrien { 54090075Sobrien int j; 54190075Sobrien 54290075Sobrien for (j = 0; j < n_clobbers; j++) 54390075Sobrien if (REGNO (recog_data.operand[i]) == REGNO (clobber_reg[j])) 54490075Sobrien { 54590075Sobrien error_for_asm (insn, "output constraint %d cannot be specified together with \"%s\" clobber", 54690075Sobrien i, reg_names [REGNO (clobber_reg[j])]); 54790075Sobrien malformed_asm = 1; 54890075Sobrien break; 54990075Sobrien } 55090075Sobrien if (j == n_clobbers) 55190075Sobrien reg_used_as_output[REGNO (recog_data.operand[i])] = 1; 55290075Sobrien } 55350397Sobrien } 55418334Speter 55518334Speter 55618334Speter /* Search for first non-popped reg. */ 55718334Speter for (i = FIRST_STACK_REG; i < LAST_STACK_REG + 1; i++) 55818334Speter if (! reg_used_as_output[i]) 55918334Speter break; 56018334Speter 56118334Speter /* If there are any other popped regs, that's an error. */ 56218334Speter for (; i < LAST_STACK_REG + 1; i++) 56318334Speter if (reg_used_as_output[i]) 56418334Speter break; 56518334Speter 56618334Speter if (i != LAST_STACK_REG + 1) 56718334Speter { 56890075Sobrien error_for_asm (insn, "output regs must be grouped at top of stack"); 56918334Speter malformed_asm = 1; 57018334Speter } 57118334Speter 57218334Speter /* Enforce rule #2: All implicitly popped input regs must be closer 57318334Speter to the top of the reg-stack than any input that is not implicitly 57450397Sobrien popped. */ 57518334Speter 57690075Sobrien memset (implicitly_dies, 0, sizeof (implicitly_dies)); 57752284Sobrien for (i = n_outputs; i < n_outputs + n_inputs; i++) 57890075Sobrien if (STACK_REG_P (recog_data.operand[i])) 57918334Speter { 58018334Speter /* An input reg is implicitly popped if it is tied to an 58150397Sobrien output, or if there is a CLOBBER for it. */ 58218334Speter int j; 58318334Speter 58418334Speter for (j = 0; j < n_clobbers; j++) 58590075Sobrien if (operands_match_p (clobber_reg[j], recog_data.operand[i])) 58618334Speter break; 58718334Speter 58852284Sobrien if (j < n_clobbers || recog_op_alt[i][alt].matches >= 0) 58990075Sobrien implicitly_dies[REGNO (recog_data.operand[i])] = 1; 59018334Speter } 59118334Speter 59218334Speter /* Search for first non-popped reg. */ 59318334Speter for (i = FIRST_STACK_REG; i < LAST_STACK_REG + 1; i++) 59418334Speter if (! implicitly_dies[i]) 59518334Speter break; 59618334Speter 59718334Speter /* If there are any other popped regs, that's an error. */ 59818334Speter for (; i < LAST_STACK_REG + 1; i++) 59918334Speter if (implicitly_dies[i]) 60018334Speter break; 60118334Speter 60218334Speter if (i != LAST_STACK_REG + 1) 60318334Speter { 60418334Speter error_for_asm (insn, 60590075Sobrien "implicitly popped regs must be grouped at top of stack"); 60618334Speter malformed_asm = 1; 60718334Speter } 60818334Speter 609132718Skan /* Enforce rule #3: If any input operand uses the "f" constraint, all 61018334Speter output constraints must use the "&" earlyclobber. 61118334Speter 61290075Sobrien ??? Detect this more deterministically by having constrain_asm_operands 61350397Sobrien record any earlyclobber. */ 61418334Speter 61552284Sobrien for (i = n_outputs; i < n_outputs + n_inputs; i++) 61652284Sobrien if (recog_op_alt[i][alt].matches == -1) 61718334Speter { 61818334Speter int j; 61918334Speter 62018334Speter for (j = 0; j < n_outputs; j++) 62190075Sobrien if (operands_match_p (recog_data.operand[j], recog_data.operand[i])) 62218334Speter { 62318334Speter error_for_asm (insn, 624169689Skan "output operand %d must use %<&%> constraint", j); 62518334Speter malformed_asm = 1; 62618334Speter } 62718334Speter } 62818334Speter 62918334Speter if (malformed_asm) 63018334Speter { 63118334Speter /* Avoid further trouble with this insn. */ 63250397Sobrien PATTERN (insn) = gen_rtx_USE (VOIDmode, const0_rtx); 633117395Skan any_malformed_asm = true; 63490075Sobrien return 0; 63518334Speter } 63618334Speter 63790075Sobrien return 1; 63818334Speter} 63918334Speter 64018334Speter/* Calculate the number of inputs and outputs in BODY, an 64118334Speter asm_operands. N_OPERANDS is the total number of operands, and 64218334Speter N_INPUTS and N_OUTPUTS are pointers to ints into which the results are 64350397Sobrien placed. */ 64418334Speter 64552284Sobrienstatic int 646132718Skanget_asm_operand_n_inputs (rtx body) 64718334Speter{ 648169689Skan switch (GET_CODE (body)) 649169689Skan { 650169689Skan case SET: 651169689Skan gcc_assert (GET_CODE (SET_SRC (body)) == ASM_OPERANDS); 652169689Skan return ASM_OPERANDS_INPUT_LENGTH (SET_SRC (body)); 653169689Skan 654169689Skan case ASM_OPERANDS: 655169689Skan return ASM_OPERANDS_INPUT_LENGTH (body); 656169689Skan 657169689Skan case PARALLEL: 658169689Skan return get_asm_operand_n_inputs (XVECEXP (body, 0, 0)); 659169689Skan 660169689Skan default: 661169689Skan gcc_unreachable (); 662169689Skan } 66318334Speter} 66418334Speter 66518334Speter/* If current function returns its result in an fp stack register, 66618334Speter return the REG. Otherwise, return 0. */ 66718334Speter 66818334Speterstatic rtx 669132718Skanstack_result (tree decl) 67018334Speter{ 67152750Sobrien rtx result; 67218334Speter 67352750Sobrien /* If the value is supposed to be returned in memory, then clearly 67452750Sobrien it is not returned in a stack register. */ 675132718Skan if (aggregate_value_p (DECL_RESULT (decl), decl)) 67652750Sobrien return 0; 67752750Sobrien 67890075Sobrien result = DECL_RTL_IF_SET (DECL_RESULT (decl)); 67990075Sobrien if (result != 0) 680169689Skan result = targetm.calls.function_value (TREE_TYPE (DECL_RESULT (decl)), 681169689Skan decl, true); 68218334Speter 68318334Speter return result != 0 && STACK_REG_P (result) ? result : 0; 68418334Speter} 68518334Speter 68618334Speter 68790075Sobrien/* 68890075Sobrien * This section deals with stack register substitution, and forms the second 68990075Sobrien * pass over the RTL. 69090075Sobrien */ 69118334Speter 69218334Speter/* Replace REG, which is a pointer to a stack reg RTX, with an RTX for 69350397Sobrien the desired hard REGNO. */ 69418334Speter 69518334Speterstatic void 696132718Skanreplace_reg (rtx *reg, int regno) 69718334Speter{ 698169689Skan gcc_assert (regno >= FIRST_STACK_REG); 699169689Skan gcc_assert (regno <= LAST_STACK_REG); 700169689Skan gcc_assert (STACK_REG_P (*reg)); 70118334Speter 702169689Skan gcc_assert (SCALAR_FLOAT_MODE_P (GET_MODE (*reg)) 703169689Skan || GET_MODE_CLASS (GET_MODE (*reg)) == MODE_COMPLEX_FLOAT); 70418334Speter 70518334Speter *reg = FP_MODE_REG (regno, GET_MODE (*reg)); 70618334Speter} 70718334Speter 70818334Speter/* Remove a note of type NOTE, which must be found, for register 70950397Sobrien number REGNO from INSN. Remove only one such note. */ 71018334Speter 71118334Speterstatic void 712132718Skanremove_regno_note (rtx insn, enum reg_note note, unsigned int regno) 71318334Speter{ 71490075Sobrien rtx *note_link, this; 71518334Speter 71690075Sobrien note_link = ®_NOTES (insn); 71718334Speter for (this = *note_link; this; this = XEXP (this, 1)) 71818334Speter if (REG_NOTE_KIND (this) == note 71918334Speter && REG_P (XEXP (this, 0)) && REGNO (XEXP (this, 0)) == regno) 72018334Speter { 72118334Speter *note_link = XEXP (this, 1); 72218334Speter return; 72318334Speter } 72418334Speter else 72518334Speter note_link = &XEXP (this, 1); 72618334Speter 727169689Skan gcc_unreachable (); 72818334Speter} 72918334Speter 73018334Speter/* Find the hard register number of virtual register REG in REGSTACK. 73118334Speter The hard register number is relative to the top of the stack. -1 is 73250397Sobrien returned if the register is not found. */ 73318334Speter 73418334Speterstatic int 735132718Skanget_hard_regnum (stack regstack, rtx reg) 73618334Speter{ 73718334Speter int i; 73818334Speter 739169689Skan gcc_assert (STACK_REG_P (reg)); 74018334Speter 74118334Speter for (i = regstack->top; i >= 0; i--) 74218334Speter if (regstack->reg[i] == REGNO (reg)) 74318334Speter break; 74418334Speter 74518334Speter return i >= 0 ? (FIRST_STACK_REG + regstack->top - i) : -1; 74618334Speter} 74718334Speter 74818334Speter/* Emit an insn to pop virtual register REG before or after INSN. 74918334Speter REGSTACK is the stack state after INSN and is updated to reflect this 75090075Sobrien pop. WHEN is either emit_insn_before or emit_insn_after. A pop insn 75190075Sobrien is represented as a SET whose destination is the register to be popped 75290075Sobrien and source is the top of stack. A death note for the top of stack 75350397Sobrien cases the movdf pattern to pop. */ 75418334Speter 75518334Speterstatic rtx 756132718Skanemit_pop_insn (rtx insn, stack regstack, rtx reg, enum emit_where where) 75718334Speter{ 75818334Speter rtx pop_insn, pop_rtx; 75918334Speter int hard_regno; 76018334Speter 76190075Sobrien /* For complex types take care to pop both halves. These may survive in 76290075Sobrien CLOBBER and USE expressions. */ 76390075Sobrien if (COMPLEX_MODE_P (GET_MODE (reg))) 76490075Sobrien { 76590075Sobrien rtx reg1 = FP_MODE_REG (REGNO (reg), DFmode); 76690075Sobrien rtx reg2 = FP_MODE_REG (REGNO (reg) + 1, DFmode); 76790075Sobrien 76890075Sobrien pop_insn = NULL_RTX; 76990075Sobrien if (get_hard_regnum (regstack, reg1) >= 0) 770117395Skan pop_insn = emit_pop_insn (insn, regstack, reg1, where); 77190075Sobrien if (get_hard_regnum (regstack, reg2) >= 0) 772117395Skan pop_insn = emit_pop_insn (insn, regstack, reg2, where); 773169689Skan gcc_assert (pop_insn); 77490075Sobrien return pop_insn; 77590075Sobrien } 77690075Sobrien 77718334Speter hard_regno = get_hard_regnum (regstack, reg); 77818334Speter 779169689Skan gcc_assert (hard_regno >= FIRST_STACK_REG); 78018334Speter 78190075Sobrien pop_rtx = gen_rtx_SET (VOIDmode, FP_MODE_REG (hard_regno, DFmode), 78290075Sobrien FP_MODE_REG (FIRST_STACK_REG, DFmode)); 78318334Speter 78490075Sobrien if (where == EMIT_AFTER) 78590075Sobrien pop_insn = emit_insn_after (pop_rtx, insn); 78690075Sobrien else 78790075Sobrien pop_insn = emit_insn_before (pop_rtx, insn); 78818334Speter 78990075Sobrien REG_NOTES (pop_insn) 79090075Sobrien = gen_rtx_EXPR_LIST (REG_DEAD, FP_MODE_REG (FIRST_STACK_REG, DFmode), 79190075Sobrien REG_NOTES (pop_insn)); 79218334Speter 79318334Speter regstack->reg[regstack->top - (hard_regno - FIRST_STACK_REG)] 79418334Speter = regstack->reg[regstack->top]; 79518334Speter regstack->top -= 1; 79618334Speter CLEAR_HARD_REG_BIT (regstack->reg_set, REGNO (reg)); 79718334Speter 79818334Speter return pop_insn; 79918334Speter} 80018334Speter 80190075Sobrien/* Emit an insn before or after INSN to swap virtual register REG with 80290075Sobrien the top of stack. REGSTACK is the stack state before the swap, and 80390075Sobrien is updated to reflect the swap. A swap insn is represented as a 80490075Sobrien PARALLEL of two patterns: each pattern moves one reg to the other. 80518334Speter 80650397Sobrien If REG is already at the top of the stack, no insn is emitted. */ 80718334Speter 80818334Speterstatic void 809132718Skanemit_swap_insn (rtx insn, stack regstack, rtx reg) 81018334Speter{ 81118334Speter int hard_regno; 81290075Sobrien rtx swap_rtx; 81318334Speter int tmp, other_reg; /* swap regno temps */ 81418334Speter rtx i1; /* the stack-reg insn prior to INSN */ 81518334Speter rtx i1set = NULL_RTX; /* the SET rtx within I1 */ 81618334Speter 81718334Speter hard_regno = get_hard_regnum (regstack, reg); 81818334Speter 81918334Speter if (hard_regno == FIRST_STACK_REG) 82018334Speter return; 821169689Skan if (hard_regno == -1) 822169689Skan { 823169689Skan /* Something failed if the register wasn't on the stack. If we had 824169689Skan malformed asms, we zapped the instruction itself, but that didn't 825169689Skan produce the same pattern of register sets as before. To prevent 826169689Skan further failure, adjust REGSTACK to include REG at TOP. */ 827169689Skan gcc_assert (any_malformed_asm); 828169689Skan regstack->reg[++regstack->top] = REGNO (reg); 829169689Skan return; 830169689Skan } 831169689Skan gcc_assert (hard_regno >= FIRST_STACK_REG); 83218334Speter 83318334Speter other_reg = regstack->top - (hard_regno - FIRST_STACK_REG); 83418334Speter 83518334Speter tmp = regstack->reg[other_reg]; 83618334Speter regstack->reg[other_reg] = regstack->reg[regstack->top]; 83718334Speter regstack->reg[regstack->top] = tmp; 83818334Speter 83990075Sobrien /* Find the previous insn involving stack regs, but don't pass a 84090075Sobrien block boundary. */ 84190075Sobrien i1 = NULL; 842132718Skan if (current_block && insn != BB_HEAD (current_block)) 84390075Sobrien { 84490075Sobrien rtx tmp = PREV_INSN (insn); 845132718Skan rtx limit = PREV_INSN (BB_HEAD (current_block)); 84690075Sobrien while (tmp != limit) 84790075Sobrien { 848169689Skan if (LABEL_P (tmp) 849169689Skan || CALL_P (tmp) 85090075Sobrien || NOTE_INSN_BASIC_BLOCK_P (tmp) 851169689Skan || (NONJUMP_INSN_P (tmp) 85290075Sobrien && stack_regs_mentioned (tmp))) 85390075Sobrien { 85490075Sobrien i1 = tmp; 85590075Sobrien break; 85690075Sobrien } 85790075Sobrien tmp = PREV_INSN (tmp); 85890075Sobrien } 85990075Sobrien } 86018334Speter 86190075Sobrien if (i1 != NULL_RTX 86290075Sobrien && (i1set = single_set (i1)) != NULL_RTX) 86318334Speter { 86418334Speter rtx i1src = *get_true_reg (&SET_SRC (i1set)); 86518334Speter rtx i1dest = *get_true_reg (&SET_DEST (i1set)); 86618334Speter 86718334Speter /* If the previous register stack push was from the reg we are to 86850397Sobrien swap with, omit the swap. */ 86918334Speter 870169689Skan if (REG_P (i1dest) && REGNO (i1dest) == FIRST_STACK_REG 871169689Skan && REG_P (i1src) 87290075Sobrien && REGNO (i1src) == (unsigned) hard_regno - 1 87318334Speter && find_regno_note (i1, REG_DEAD, FIRST_STACK_REG) == NULL_RTX) 87418334Speter return; 87518334Speter 87618334Speter /* If the previous insn wrote to the reg we are to swap with, 87718334Speter omit the swap. */ 87818334Speter 879169689Skan if (REG_P (i1dest) && REGNO (i1dest) == (unsigned) hard_regno 880169689Skan && REG_P (i1src) && REGNO (i1src) == FIRST_STACK_REG 88118334Speter && find_regno_note (i1, REG_DEAD, FIRST_STACK_REG) == NULL_RTX) 88218334Speter return; 88318334Speter } 88418334Speter 885169689Skan /* Avoid emitting the swap if this is the first register stack insn 886169689Skan of the current_block. Instead update the current_block's stack_in 887169689Skan and let compensate edges take care of this for us. */ 888169689Skan if (current_block && starting_stack_p) 889169689Skan { 890169689Skan BLOCK_INFO (current_block)->stack_in = *regstack; 891169689Skan starting_stack_p = false; 892169689Skan return; 893169689Skan } 894169689Skan 89590075Sobrien swap_rtx = gen_swapxf (FP_MODE_REG (hard_regno, XFmode), 89690075Sobrien FP_MODE_REG (FIRST_STACK_REG, XFmode)); 89718334Speter 89890075Sobrien if (i1) 89990075Sobrien emit_insn_after (swap_rtx, i1); 90090075Sobrien else if (current_block) 901132718Skan emit_insn_before (swap_rtx, BB_HEAD (current_block)); 90290075Sobrien else 90390075Sobrien emit_insn_before (swap_rtx, insn); 90418334Speter} 90518334Speter 906169689Skan/* Emit an insns before INSN to swap virtual register SRC1 with 907169689Skan the top of stack and virtual register SRC2 with second stack 908169689Skan slot. REGSTACK is the stack state before the swaps, and 909169689Skan is updated to reflect the swaps. A swap insn is represented as a 910169689Skan PARALLEL of two patterns: each pattern moves one reg to the other. 911169689Skan 912169689Skan If SRC1 and/or SRC2 are already at the right place, no swap insn 913169689Skan is emitted. */ 914169689Skan 915169689Skanstatic void 916169689Skanswap_to_top (rtx insn, stack regstack, rtx src1, rtx src2) 917169689Skan{ 918169689Skan struct stack_def temp_stack; 919169689Skan int regno, j, k, temp; 920169689Skan 921169689Skan temp_stack = *regstack; 922169689Skan 923169689Skan /* Place operand 1 at the top of stack. */ 924169689Skan regno = get_hard_regnum (&temp_stack, src1); 925169689Skan gcc_assert (regno >= 0); 926169689Skan if (regno != FIRST_STACK_REG) 927169689Skan { 928169689Skan k = temp_stack.top - (regno - FIRST_STACK_REG); 929169689Skan j = temp_stack.top; 930169689Skan 931169689Skan temp = temp_stack.reg[k]; 932169689Skan temp_stack.reg[k] = temp_stack.reg[j]; 933169689Skan temp_stack.reg[j] = temp; 934169689Skan } 935169689Skan 936169689Skan /* Place operand 2 next on the stack. */ 937169689Skan regno = get_hard_regnum (&temp_stack, src2); 938169689Skan gcc_assert (regno >= 0); 939169689Skan if (regno != FIRST_STACK_REG + 1) 940169689Skan { 941169689Skan k = temp_stack.top - (regno - FIRST_STACK_REG); 942169689Skan j = temp_stack.top - 1; 943169689Skan 944169689Skan temp = temp_stack.reg[k]; 945169689Skan temp_stack.reg[k] = temp_stack.reg[j]; 946169689Skan temp_stack.reg[j] = temp; 947169689Skan } 948169689Skan 949169689Skan change_stack (insn, regstack, &temp_stack, EMIT_BEFORE); 950169689Skan} 951169689Skan 95218334Speter/* Handle a move to or from a stack register in PAT, which is in INSN. 953132718Skan REGSTACK is the current stack. Return whether a control flow insn 954132718Skan was deleted in the process. */ 95518334Speter 956132718Skanstatic bool 957132718Skanmove_for_stack_reg (rtx insn, stack regstack, rtx pat) 95818334Speter{ 95918334Speter rtx *psrc = get_true_reg (&SET_SRC (pat)); 96018334Speter rtx *pdest = get_true_reg (&SET_DEST (pat)); 96118334Speter rtx src, dest; 96218334Speter rtx note; 963132718Skan bool control_flow_insn_deleted = false; 96418334Speter 96518334Speter src = *psrc; dest = *pdest; 96618334Speter 96718334Speter if (STACK_REG_P (src) && STACK_REG_P (dest)) 96818334Speter { 96918334Speter /* Write from one stack reg to another. If SRC dies here, then 97050397Sobrien just change the register mapping and delete the insn. */ 97118334Speter 97218334Speter note = find_regno_note (insn, REG_DEAD, REGNO (src)); 97318334Speter if (note) 97418334Speter { 97518334Speter int i; 97618334Speter 97750397Sobrien /* If this is a no-op move, there must not be a REG_DEAD note. */ 978169689Skan gcc_assert (REGNO (src) != REGNO (dest)); 97918334Speter 98018334Speter for (i = regstack->top; i >= 0; i--) 98118334Speter if (regstack->reg[i] == REGNO (src)) 98218334Speter break; 98318334Speter 984146895Skan /* The destination must be dead, or life analysis is borked. */ 985169689Skan gcc_assert (get_hard_regnum (regstack, dest) < FIRST_STACK_REG); 98618334Speter 987146895Skan /* If the source is not live, this is yet another case of 988146895Skan uninitialized variables. Load up a NaN instead. */ 989146895Skan if (i < 0) 990169689Skan return move_nan_for_stack_reg (insn, regstack, dest); 991146895Skan 99218334Speter /* It is possible that the dest is unused after this insn. 99350397Sobrien If so, just pop the src. */ 99418334Speter 99518334Speter if (find_regno_note (insn, REG_UNUSED, REGNO (dest))) 996132718Skan emit_pop_insn (insn, regstack, src, EMIT_AFTER); 997132718Skan else 99818334Speter { 999132718Skan regstack->reg[i] = REGNO (dest); 1000132718Skan SET_HARD_REG_BIT (regstack->reg_set, REGNO (dest)); 1001132718Skan CLEAR_HARD_REG_BIT (regstack->reg_set, REGNO (src)); 100218334Speter } 100318334Speter 1004132718Skan control_flow_insn_deleted |= control_flow_insn_p (insn); 100590075Sobrien delete_insn (insn); 1006132718Skan return control_flow_insn_deleted; 100718334Speter } 100818334Speter 100950397Sobrien /* The source reg does not die. */ 101018334Speter 101118334Speter /* If this appears to be a no-op move, delete it, or else it 101218334Speter will confuse the machine description output patterns. But if 101318334Speter it is REG_UNUSED, we must pop the reg now, as per-insn processing 101450397Sobrien for REG_UNUSED will not work for deleted insns. */ 101518334Speter 101618334Speter if (REGNO (src) == REGNO (dest)) 101718334Speter { 101818334Speter if (find_regno_note (insn, REG_UNUSED, REGNO (dest))) 101990075Sobrien emit_pop_insn (insn, regstack, dest, EMIT_AFTER); 102018334Speter 1021132718Skan control_flow_insn_deleted |= control_flow_insn_p (insn); 102290075Sobrien delete_insn (insn); 1023132718Skan return control_flow_insn_deleted; 102418334Speter } 102518334Speter 1026117395Skan /* The destination ought to be dead. */ 1027169689Skan gcc_assert (get_hard_regnum (regstack, dest) < FIRST_STACK_REG); 102818334Speter 102918334Speter replace_reg (psrc, get_hard_regnum (regstack, src)); 103018334Speter 103118334Speter regstack->reg[++regstack->top] = REGNO (dest); 103218334Speter SET_HARD_REG_BIT (regstack->reg_set, REGNO (dest)); 103318334Speter replace_reg (pdest, FIRST_STACK_REG); 103418334Speter } 103518334Speter else if (STACK_REG_P (src)) 103618334Speter { 103718334Speter /* Save from a stack reg to MEM, or possibly integer reg. Since 103818334Speter only top of stack may be saved, emit an exchange first if 103950397Sobrien needs be. */ 104018334Speter 104118334Speter emit_swap_insn (insn, regstack, src); 104218334Speter 104318334Speter note = find_regno_note (insn, REG_DEAD, REGNO (src)); 104418334Speter if (note) 104518334Speter { 104618334Speter replace_reg (&XEXP (note, 0), FIRST_STACK_REG); 104718334Speter regstack->top--; 104818334Speter CLEAR_HARD_REG_BIT (regstack->reg_set, REGNO (src)); 104918334Speter } 1050132718Skan else if ((GET_MODE (src) == XFmode) 105190075Sobrien && regstack->top < REG_STACK_SIZE - 1) 105218334Speter { 105318334Speter /* A 387 cannot write an XFmode value to a MEM without 105418334Speter clobbering the source reg. The output code can handle 105518334Speter this by reading back the value from the MEM. 105618334Speter But it is more efficient to use a temp register if one is 105718334Speter available. Push the source value here if the register 105818334Speter stack is not full, and then write the value to memory via 105918334Speter a pop. */ 1060169689Skan rtx push_rtx; 106190075Sobrien rtx top_stack_reg = FP_MODE_REG (FIRST_STACK_REG, GET_MODE (src)); 106218334Speter 1063132718Skan push_rtx = gen_movxf (top_stack_reg, top_stack_reg); 1064169689Skan emit_insn_before (push_rtx, insn); 106550397Sobrien REG_NOTES (insn) = gen_rtx_EXPR_LIST (REG_DEAD, top_stack_reg, 106650397Sobrien REG_NOTES (insn)); 106718334Speter } 106818334Speter 106918334Speter replace_reg (psrc, FIRST_STACK_REG); 107018334Speter } 1071169689Skan else 107218334Speter { 1073169689Skan gcc_assert (STACK_REG_P (dest)); 1074169689Skan 107518334Speter /* Load from MEM, or possibly integer REG or constant, into the 107618334Speter stack regs. The actual target is always the top of the 107718334Speter stack. The stack mapping is changed to reflect that DEST is 107818334Speter now at top of stack. */ 107918334Speter 1080117395Skan /* The destination ought to be dead. */ 1081169689Skan gcc_assert (get_hard_regnum (regstack, dest) < FIRST_STACK_REG); 108218334Speter 1083169689Skan gcc_assert (regstack->top < REG_STACK_SIZE); 108418334Speter 108518334Speter regstack->reg[++regstack->top] = REGNO (dest); 108618334Speter SET_HARD_REG_BIT (regstack->reg_set, REGNO (dest)); 108718334Speter replace_reg (pdest, FIRST_STACK_REG); 108818334Speter } 1089132718Skan 1090132718Skan return control_flow_insn_deleted; 109118334Speter} 1092169689Skan 1093169689Skan/* A helper function which replaces INSN with a pattern that loads up 1094169689Skan a NaN into DEST, then invokes move_for_stack_reg. */ 1095169689Skan 1096169689Skanstatic bool 1097169689Skanmove_nan_for_stack_reg (rtx insn, stack regstack, rtx dest) 1098169689Skan{ 1099169689Skan rtx pat; 1100169689Skan 1101169689Skan dest = FP_MODE_REG (REGNO (dest), SFmode); 1102169689Skan pat = gen_rtx_SET (VOIDmode, dest, not_a_num); 1103169689Skan PATTERN (insn) = pat; 1104169689Skan INSN_CODE (insn) = -1; 1105169689Skan 1106169689Skan return move_for_stack_reg (insn, regstack, pat); 1107169689Skan} 110818334Speter 110990075Sobrien/* Swap the condition on a branch, if there is one. Return true if we 111090075Sobrien found a condition to swap. False if the condition was not used as 111190075Sobrien such. */ 111290075Sobrien 111390075Sobrienstatic int 1114132718Skanswap_rtx_condition_1 (rtx pat) 111518334Speter{ 111690075Sobrien const char *fmt; 111790075Sobrien int i, r = 0; 111818334Speter 1119169689Skan if (COMPARISON_P (pat)) 112018334Speter { 112118334Speter PUT_CODE (pat, swap_condition (GET_CODE (pat))); 112290075Sobrien r = 1; 112318334Speter } 112490075Sobrien else 112590075Sobrien { 112690075Sobrien fmt = GET_RTX_FORMAT (GET_CODE (pat)); 112790075Sobrien for (i = GET_RTX_LENGTH (GET_CODE (pat)) - 1; i >= 0; i--) 112890075Sobrien { 112990075Sobrien if (fmt[i] == 'E') 113090075Sobrien { 113190075Sobrien int j; 113218334Speter 113390075Sobrien for (j = XVECLEN (pat, i) - 1; j >= 0; j--) 113490075Sobrien r |= swap_rtx_condition_1 (XVECEXP (pat, i, j)); 113590075Sobrien } 113690075Sobrien else if (fmt[i] == 'e') 113790075Sobrien r |= swap_rtx_condition_1 (XEXP (pat, i)); 113890075Sobrien } 113990075Sobrien } 114090075Sobrien 114190075Sobrien return r; 114290075Sobrien} 114390075Sobrien 114490075Sobrienstatic int 1145132718Skanswap_rtx_condition (rtx insn) 114690075Sobrien{ 114790075Sobrien rtx pat = PATTERN (insn); 114890075Sobrien 114990075Sobrien /* We're looking for a single set to cc0 or an HImode temporary. */ 115090075Sobrien 115190075Sobrien if (GET_CODE (pat) == SET 1152169689Skan && REG_P (SET_DEST (pat)) 115390075Sobrien && REGNO (SET_DEST (pat)) == FLAGS_REG) 115418334Speter { 115590075Sobrien insn = next_flags_user (insn); 115690075Sobrien if (insn == NULL_RTX) 115790075Sobrien return 0; 115890075Sobrien pat = PATTERN (insn); 115990075Sobrien } 116090075Sobrien 1161161651Skan /* See if this is, or ends in, a fnstsw. If so, we're not doing anything 1162161651Skan with the cc value right now. We may be able to search for one 1163161651Skan though. */ 116490075Sobrien 116590075Sobrien if (GET_CODE (pat) == SET 116690075Sobrien && GET_CODE (SET_SRC (pat)) == UNSPEC 1167117395Skan && XINT (SET_SRC (pat), 1) == UNSPEC_FNSTSW) 116890075Sobrien { 116990075Sobrien rtx dest = SET_DEST (pat); 117090075Sobrien 1171117395Skan /* Search forward looking for the first use of this value. 117290075Sobrien Stop at block boundaries. */ 1173132718Skan while (insn != BB_END (current_block)) 117418334Speter { 117590075Sobrien insn = NEXT_INSN (insn); 117690075Sobrien if (INSN_P (insn) && reg_mentioned_p (dest, insn)) 117790075Sobrien break; 1178169689Skan if (CALL_P (insn)) 117990075Sobrien return 0; 118090075Sobrien } 118118334Speter 1182161651Skan /* We haven't found it. */ 1183161651Skan if (insn == BB_END (current_block)) 1184161651Skan return 0; 1185161651Skan 118690075Sobrien /* So we've found the insn using this value. If it is anything 1187161651Skan other than sahf or the value does not die (meaning we'd have 1188161651Skan to search further), then we must give up. */ 118990075Sobrien pat = PATTERN (insn); 119090075Sobrien if (GET_CODE (pat) != SET 119190075Sobrien || GET_CODE (SET_SRC (pat)) != UNSPEC 1192117395Skan || XINT (SET_SRC (pat), 1) != UNSPEC_SAHF 119390075Sobrien || ! dead_or_set_p (insn, dest)) 119490075Sobrien return 0; 119590075Sobrien 119690075Sobrien /* Now we are prepared to handle this as a normal cc0 setter. */ 119790075Sobrien insn = next_flags_user (insn); 119890075Sobrien if (insn == NULL_RTX) 119990075Sobrien return 0; 120090075Sobrien pat = PATTERN (insn); 120190075Sobrien } 120290075Sobrien 120390075Sobrien if (swap_rtx_condition_1 (pat)) 120490075Sobrien { 120590075Sobrien int fail = 0; 120690075Sobrien INSN_CODE (insn) = -1; 120790075Sobrien if (recog_memoized (insn) == -1) 120890075Sobrien fail = 1; 120990075Sobrien /* In case the flags don't die here, recurse to try fix 121090075Sobrien following user too. */ 121190075Sobrien else if (! dead_or_set_p (insn, ix86_flags_rtx)) 121290075Sobrien { 121390075Sobrien insn = next_flags_user (insn); 121490075Sobrien if (!insn || !swap_rtx_condition (insn)) 121590075Sobrien fail = 1; 121618334Speter } 121790075Sobrien if (fail) 121890075Sobrien { 121990075Sobrien swap_rtx_condition_1 (pat); 122090075Sobrien return 0; 122190075Sobrien } 122290075Sobrien return 1; 122318334Speter } 122490075Sobrien return 0; 122518334Speter} 122618334Speter 122718334Speter/* Handle a comparison. Special care needs to be taken to avoid 122818334Speter causing comparisons that a 387 cannot do correctly, such as EQ. 122918334Speter 123090075Sobrien Also, a pop insn may need to be emitted. The 387 does have an 123118334Speter `fcompp' insn that can pop two regs, but it is sometimes too expensive 123218334Speter to do this - a `fcomp' followed by a `fstpl %st(0)' may be easier to 123390075Sobrien set up. */ 123418334Speter 123518334Speterstatic void 1236132718Skancompare_for_stack_reg (rtx insn, stack regstack, rtx pat_src) 123718334Speter{ 123818334Speter rtx *src1, *src2; 123918334Speter rtx src1_note, src2_note; 124018334Speter 124190075Sobrien src1 = get_true_reg (&XEXP (pat_src, 0)); 124290075Sobrien src2 = get_true_reg (&XEXP (pat_src, 1)); 124318334Speter 124418334Speter /* ??? If fxch turns out to be cheaper than fstp, give priority to 124550397Sobrien registers that die in this insn - move those to stack top first. */ 124690075Sobrien if ((! STACK_REG_P (*src1) 124790075Sobrien || (STACK_REG_P (*src2) 124890075Sobrien && get_hard_regnum (regstack, *src2) == FIRST_STACK_REG)) 124990075Sobrien && swap_rtx_condition (insn)) 125018334Speter { 125190075Sobrien rtx temp; 125290075Sobrien temp = XEXP (pat_src, 0); 125390075Sobrien XEXP (pat_src, 0) = XEXP (pat_src, 1); 125490075Sobrien XEXP (pat_src, 1) = temp; 125518334Speter 125690075Sobrien src1 = get_true_reg (&XEXP (pat_src, 0)); 125790075Sobrien src2 = get_true_reg (&XEXP (pat_src, 1)); 125818334Speter 125918334Speter INSN_CODE (insn) = -1; 126018334Speter } 126118334Speter 126250397Sobrien /* We will fix any death note later. */ 126318334Speter 126418334Speter src1_note = find_regno_note (insn, REG_DEAD, REGNO (*src1)); 126518334Speter 126618334Speter if (STACK_REG_P (*src2)) 126718334Speter src2_note = find_regno_note (insn, REG_DEAD, REGNO (*src2)); 126818334Speter else 126918334Speter src2_note = NULL_RTX; 127018334Speter 127190075Sobrien emit_swap_insn (insn, regstack, *src1); 127218334Speter 127318334Speter replace_reg (src1, FIRST_STACK_REG); 127418334Speter 127518334Speter if (STACK_REG_P (*src2)) 127690075Sobrien replace_reg (src2, get_hard_regnum (regstack, *src2)); 127718334Speter 127818334Speter if (src1_note) 127918334Speter { 128050397Sobrien pop_stack (regstack, REGNO (XEXP (src1_note, 0))); 128118334Speter replace_reg (&XEXP (src1_note, 0), FIRST_STACK_REG); 128218334Speter } 128318334Speter 128418334Speter /* If the second operand dies, handle that. But if the operands are 128518334Speter the same stack register, don't bother, because only one death is 128650397Sobrien needed, and it was just handled. */ 128718334Speter 128818334Speter if (src2_note 128918334Speter && ! (STACK_REG_P (*src1) && STACK_REG_P (*src2) 129018334Speter && REGNO (*src1) == REGNO (*src2))) 129118334Speter { 129218334Speter /* As a special case, two regs may die in this insn if src2 is 129318334Speter next to top of stack and the top of stack also dies. Since 129418334Speter we have already popped src1, "next to top of stack" is really 129550397Sobrien at top (FIRST_STACK_REG) now. */ 129618334Speter 129718334Speter if (get_hard_regnum (regstack, XEXP (src2_note, 0)) == FIRST_STACK_REG 129818334Speter && src1_note) 129918334Speter { 130050397Sobrien pop_stack (regstack, REGNO (XEXP (src2_note, 0))); 130118334Speter replace_reg (&XEXP (src2_note, 0), FIRST_STACK_REG + 1); 130218334Speter } 130318334Speter else 130418334Speter { 130590075Sobrien /* The 386 can only represent death of the first operand in 130690075Sobrien the case handled above. In all other cases, emit a separate 130790075Sobrien pop and remove the death note from here. */ 130818334Speter 130990075Sobrien /* link_cc0_insns (insn); */ 131090075Sobrien 131190075Sobrien remove_regno_note (insn, REG_DEAD, REGNO (XEXP (src2_note, 0))); 131290075Sobrien 131390075Sobrien emit_pop_insn (insn, regstack, XEXP (src2_note, 0), 131490075Sobrien EMIT_AFTER); 131518334Speter } 131618334Speter } 131718334Speter} 131818334Speter 131918334Speter/* Substitute new registers in PAT, which is part of INSN. REGSTACK 1320132718Skan is the current register layout. Return whether a control flow insn 1321132718Skan was deleted in the process. */ 132218334Speter 1323132718Skanstatic bool 1324132718Skansubst_stack_regs_pat (rtx insn, stack regstack, rtx pat) 132518334Speter{ 132618334Speter rtx *dest, *src; 1327132718Skan bool control_flow_insn_deleted = false; 132818334Speter 132990075Sobrien switch (GET_CODE (pat)) 133090075Sobrien { 133190075Sobrien case USE: 133290075Sobrien /* Deaths in USE insns can happen in non optimizing compilation. 133390075Sobrien Handle them by popping the dying register. */ 133490075Sobrien src = get_true_reg (&XEXP (pat, 0)); 1335117395Skan if (STACK_REG_P (*src) 1336117395Skan && find_regno_note (insn, REG_DEAD, REGNO (*src))) 1337117395Skan { 1338117395Skan emit_pop_insn (insn, regstack, *src, EMIT_AFTER); 1339132718Skan return control_flow_insn_deleted; 1340117395Skan } 134190075Sobrien /* ??? Uninitialized USE should not happen. */ 1342169689Skan else 1343169689Skan gcc_assert (get_hard_regnum (regstack, *src) != -1); 134490075Sobrien break; 134518334Speter 134690075Sobrien case CLOBBER: 134790075Sobrien { 134890075Sobrien rtx note; 134918334Speter 135090075Sobrien dest = get_true_reg (&XEXP (pat, 0)); 135190075Sobrien if (STACK_REG_P (*dest)) 135290075Sobrien { 135390075Sobrien note = find_reg_note (insn, REG_DEAD, *dest); 135418334Speter 135590075Sobrien if (pat != PATTERN (insn)) 135690075Sobrien { 135790075Sobrien /* The fix_truncdi_1 pattern wants to be able to allocate 1358169689Skan its own scratch register. It does this by clobbering 135990075Sobrien an fp reg so that it is assured of an empty reg-stack 1360117395Skan register. If the register is live, kill it now. 136190075Sobrien Remove the DEAD/UNUSED note so we don't try to kill it 136290075Sobrien later too. */ 136390075Sobrien 136490075Sobrien if (note) 136590075Sobrien emit_pop_insn (insn, regstack, *dest, EMIT_BEFORE); 136690075Sobrien else 136790075Sobrien { 136890075Sobrien note = find_reg_note (insn, REG_UNUSED, *dest); 1369169689Skan gcc_assert (note); 137090075Sobrien } 137190075Sobrien remove_note (insn, note); 1372132718Skan replace_reg (dest, FIRST_STACK_REG + 1); 137390075Sobrien } 137490075Sobrien else 137590075Sobrien { 137690075Sobrien /* A top-level clobber with no REG_DEAD, and no hard-regnum 137790075Sobrien indicates an uninitialized value. Because reload removed 1378117395Skan all other clobbers, this must be due to a function 137990075Sobrien returning without a value. Load up a NaN. */ 138090075Sobrien 1381169689Skan if (!note) 138290075Sobrien { 1383169689Skan rtx t = *dest; 1384169689Skan if (COMPLEX_MODE_P (GET_MODE (t))) 1385169689Skan { 1386169689Skan rtx u = FP_MODE_REG (REGNO (t) + 1, SFmode); 1387169689Skan if (get_hard_regnum (regstack, u) == -1) 1388169689Skan { 1389169689Skan rtx pat2 = gen_rtx_CLOBBER (VOIDmode, u); 1390169689Skan rtx insn2 = emit_insn_before (pat2, insn); 1391169689Skan control_flow_insn_deleted 1392169689Skan |= move_nan_for_stack_reg (insn2, regstack, u); 1393169689Skan } 1394169689Skan } 1395169689Skan if (get_hard_regnum (regstack, t) == -1) 1396169689Skan control_flow_insn_deleted 1397169689Skan |= move_nan_for_stack_reg (insn, regstack, t); 139890075Sobrien } 139990075Sobrien } 140090075Sobrien } 140118334Speter break; 140290075Sobrien } 140318334Speter 140490075Sobrien case SET: 140590075Sobrien { 140690075Sobrien rtx *src1 = (rtx *) 0, *src2; 140790075Sobrien rtx src1_note, src2_note; 140890075Sobrien rtx pat_src; 140990075Sobrien 141090075Sobrien dest = get_true_reg (&SET_DEST (pat)); 141190075Sobrien src = get_true_reg (&SET_SRC (pat)); 141290075Sobrien pat_src = SET_SRC (pat); 141390075Sobrien 141490075Sobrien /* See if this is a `movM' pattern, and handle elsewhere if so. */ 141590075Sobrien if (STACK_REG_P (*src) 141690075Sobrien || (STACK_REG_P (*dest) 1417169689Skan && (REG_P (*src) || MEM_P (*src) 141890075Sobrien || GET_CODE (*src) == CONST_DOUBLE))) 141990075Sobrien { 1420132718Skan control_flow_insn_deleted |= move_for_stack_reg (insn, regstack, pat); 142190075Sobrien break; 142290075Sobrien } 142390075Sobrien 142490075Sobrien switch (GET_CODE (pat_src)) 142590075Sobrien { 142690075Sobrien case COMPARE: 142790075Sobrien compare_for_stack_reg (insn, regstack, pat_src); 142890075Sobrien break; 142990075Sobrien 143090075Sobrien case CALL: 143118334Speter { 143290075Sobrien int count; 1433169689Skan for (count = hard_regno_nregs[REGNO (*dest)][GET_MODE (*dest)]; 143490075Sobrien --count >= 0;) 143590075Sobrien { 143690075Sobrien regstack->reg[++regstack->top] = REGNO (*dest) + count; 143790075Sobrien SET_HARD_REG_BIT (regstack->reg_set, REGNO (*dest) + count); 143890075Sobrien } 143918334Speter } 144090075Sobrien replace_reg (dest, FIRST_STACK_REG); 144190075Sobrien break; 144218334Speter 144390075Sobrien case REG: 144490075Sobrien /* This is a `tstM2' case. */ 1445169689Skan gcc_assert (*dest == cc0_rtx); 144690075Sobrien src1 = src; 144718334Speter 144890075Sobrien /* Fall through. */ 144918334Speter 145090075Sobrien case FLOAT_TRUNCATE: 145190075Sobrien case SQRT: 145290075Sobrien case ABS: 145390075Sobrien case NEG: 145490075Sobrien /* These insns only operate on the top of the stack. DEST might 145590075Sobrien be cc0_rtx if we're processing a tstM pattern. Also, it's 145690075Sobrien possible that the tstM case results in a REG_DEAD note on the 145790075Sobrien source. */ 145818334Speter 145990075Sobrien if (src1 == 0) 146090075Sobrien src1 = get_true_reg (&XEXP (pat_src, 0)); 146118334Speter 146290075Sobrien emit_swap_insn (insn, regstack, *src1); 146318334Speter 146490075Sobrien src1_note = find_regno_note (insn, REG_DEAD, REGNO (*src1)); 146518334Speter 146690075Sobrien if (STACK_REG_P (*dest)) 146790075Sobrien replace_reg (dest, FIRST_STACK_REG); 146818334Speter 146990075Sobrien if (src1_note) 147090075Sobrien { 147190075Sobrien replace_reg (&XEXP (src1_note, 0), FIRST_STACK_REG); 147290075Sobrien regstack->top--; 147390075Sobrien CLEAR_HARD_REG_BIT (regstack->reg_set, REGNO (*src1)); 147490075Sobrien } 147518334Speter 147690075Sobrien replace_reg (src1, FIRST_STACK_REG); 147790075Sobrien break; 147818334Speter 147990075Sobrien case MINUS: 148090075Sobrien case DIV: 148190075Sobrien /* On i386, reversed forms of subM3 and divM3 exist for 148290075Sobrien MODE_FLOAT, so the same code that works for addM3 and mulM3 148390075Sobrien can be used. */ 148490075Sobrien case MULT: 148590075Sobrien case PLUS: 148690075Sobrien /* These insns can accept the top of stack as a destination 148790075Sobrien from a stack reg or mem, or can use the top of stack as a 148890075Sobrien source and some other stack register (possibly top of stack) 148990075Sobrien as a destination. */ 149018334Speter 149190075Sobrien src1 = get_true_reg (&XEXP (pat_src, 0)); 149290075Sobrien src2 = get_true_reg (&XEXP (pat_src, 1)); 149318334Speter 149490075Sobrien /* We will fix any death note later. */ 149518334Speter 149690075Sobrien if (STACK_REG_P (*src1)) 149790075Sobrien src1_note = find_regno_note (insn, REG_DEAD, REGNO (*src1)); 149890075Sobrien else 149990075Sobrien src1_note = NULL_RTX; 150090075Sobrien if (STACK_REG_P (*src2)) 150190075Sobrien src2_note = find_regno_note (insn, REG_DEAD, REGNO (*src2)); 150290075Sobrien else 150390075Sobrien src2_note = NULL_RTX; 150418334Speter 150590075Sobrien /* If either operand is not a stack register, then the dest 150690075Sobrien must be top of stack. */ 150718334Speter 150890075Sobrien if (! STACK_REG_P (*src1) || ! STACK_REG_P (*src2)) 150990075Sobrien emit_swap_insn (insn, regstack, *dest); 151090075Sobrien else 151190075Sobrien { 151290075Sobrien /* Both operands are REG. If neither operand is already 151390075Sobrien at the top of stack, choose to make the one that is the dest 151490075Sobrien the new top of stack. */ 151518334Speter 151690075Sobrien int src1_hard_regnum, src2_hard_regnum; 151718334Speter 151890075Sobrien src1_hard_regnum = get_hard_regnum (regstack, *src1); 151990075Sobrien src2_hard_regnum = get_hard_regnum (regstack, *src2); 1520169689Skan gcc_assert (src1_hard_regnum != -1); 1521169689Skan gcc_assert (src2_hard_regnum != -1); 152218334Speter 152390075Sobrien if (src1_hard_regnum != FIRST_STACK_REG 152490075Sobrien && src2_hard_regnum != FIRST_STACK_REG) 152590075Sobrien emit_swap_insn (insn, regstack, *dest); 152690075Sobrien } 152718334Speter 152890075Sobrien if (STACK_REG_P (*src1)) 152990075Sobrien replace_reg (src1, get_hard_regnum (regstack, *src1)); 153090075Sobrien if (STACK_REG_P (*src2)) 153190075Sobrien replace_reg (src2, get_hard_regnum (regstack, *src2)); 153218334Speter 153390075Sobrien if (src1_note) 153490075Sobrien { 153590075Sobrien rtx src1_reg = XEXP (src1_note, 0); 153618334Speter 153790075Sobrien /* If the register that dies is at the top of stack, then 153890075Sobrien the destination is somewhere else - merely substitute it. 153990075Sobrien But if the reg that dies is not at top of stack, then 154090075Sobrien move the top of stack to the dead reg, as though we had 154190075Sobrien done the insn and then a store-with-pop. */ 154218334Speter 154390075Sobrien if (REGNO (src1_reg) == regstack->reg[regstack->top]) 154490075Sobrien { 154590075Sobrien SET_HARD_REG_BIT (regstack->reg_set, REGNO (*dest)); 154690075Sobrien replace_reg (dest, get_hard_regnum (regstack, *dest)); 154790075Sobrien } 154890075Sobrien else 154990075Sobrien { 155090075Sobrien int regno = get_hard_regnum (regstack, src1_reg); 155118334Speter 155290075Sobrien SET_HARD_REG_BIT (regstack->reg_set, REGNO (*dest)); 155390075Sobrien replace_reg (dest, regno); 155490075Sobrien 155590075Sobrien regstack->reg[regstack->top - (regno - FIRST_STACK_REG)] 155690075Sobrien = regstack->reg[regstack->top]; 155790075Sobrien } 155890075Sobrien 155990075Sobrien CLEAR_HARD_REG_BIT (regstack->reg_set, 156090075Sobrien REGNO (XEXP (src1_note, 0))); 156190075Sobrien replace_reg (&XEXP (src1_note, 0), FIRST_STACK_REG); 156290075Sobrien regstack->top--; 156318334Speter } 156490075Sobrien else if (src2_note) 156518334Speter { 156690075Sobrien rtx src2_reg = XEXP (src2_note, 0); 156790075Sobrien if (REGNO (src2_reg) == regstack->reg[regstack->top]) 156890075Sobrien { 156990075Sobrien SET_HARD_REG_BIT (regstack->reg_set, REGNO (*dest)); 157090075Sobrien replace_reg (dest, get_hard_regnum (regstack, *dest)); 157190075Sobrien } 157290075Sobrien else 157390075Sobrien { 157490075Sobrien int regno = get_hard_regnum (regstack, src2_reg); 157518334Speter 157690075Sobrien SET_HARD_REG_BIT (regstack->reg_set, REGNO (*dest)); 157790075Sobrien replace_reg (dest, regno); 157818334Speter 157990075Sobrien regstack->reg[regstack->top - (regno - FIRST_STACK_REG)] 158090075Sobrien = regstack->reg[regstack->top]; 158190075Sobrien } 158290075Sobrien 158390075Sobrien CLEAR_HARD_REG_BIT (regstack->reg_set, 158490075Sobrien REGNO (XEXP (src2_note, 0))); 158590075Sobrien replace_reg (&XEXP (src2_note, 0), FIRST_STACK_REG); 158690075Sobrien regstack->top--; 158718334Speter } 158890075Sobrien else 158918334Speter { 159018334Speter SET_HARD_REG_BIT (regstack->reg_set, REGNO (*dest)); 159118334Speter replace_reg (dest, get_hard_regnum (regstack, *dest)); 159218334Speter } 159390075Sobrien 1594132718Skan /* Keep operand 1 matching with destination. */ 1595169689Skan if (COMMUTATIVE_ARITH_P (pat_src) 159690075Sobrien && REG_P (*src1) && REG_P (*src2) 159790075Sobrien && REGNO (*src1) != REGNO (*dest)) 159890075Sobrien { 159990075Sobrien int tmp = REGNO (*src1); 160090075Sobrien replace_reg (src1, REGNO (*src2)); 160190075Sobrien replace_reg (src2, tmp); 160290075Sobrien } 160390075Sobrien break; 160490075Sobrien 160590075Sobrien case UNSPEC: 160690075Sobrien switch (XINT (pat_src, 1)) 160718334Speter { 1608169689Skan case UNSPEC_FIST: 1609169689Skan 1610169689Skan case UNSPEC_FIST_FLOOR: 1611169689Skan case UNSPEC_FIST_CEIL: 1612169689Skan 161390075Sobrien /* These insns only operate on the top of the stack. */ 161418334Speter 161590075Sobrien src1 = get_true_reg (&XVECEXP (pat_src, 0, 0)); 161690075Sobrien emit_swap_insn (insn, regstack, *src1); 161718334Speter 161890075Sobrien src1_note = find_regno_note (insn, REG_DEAD, REGNO (*src1)); 161918334Speter 162090075Sobrien if (STACK_REG_P (*dest)) 162190075Sobrien replace_reg (dest, FIRST_STACK_REG); 162218334Speter 162390075Sobrien if (src1_note) 162490075Sobrien { 162590075Sobrien replace_reg (&XEXP (src1_note, 0), FIRST_STACK_REG); 162690075Sobrien regstack->top--; 162790075Sobrien CLEAR_HARD_REG_BIT (regstack->reg_set, REGNO (*src1)); 162890075Sobrien } 162918334Speter 163090075Sobrien replace_reg (src1, FIRST_STACK_REG); 163190075Sobrien break; 163218334Speter 1633169689Skan case UNSPEC_SIN: 1634169689Skan case UNSPEC_COS: 1635169689Skan case UNSPEC_FRNDINT: 1636169689Skan case UNSPEC_F2XM1: 1637169689Skan 1638169689Skan case UNSPEC_FRNDINT_FLOOR: 1639169689Skan case UNSPEC_FRNDINT_CEIL: 1640169689Skan case UNSPEC_FRNDINT_TRUNC: 1641169689Skan case UNSPEC_FRNDINT_MASK_PM: 1642169689Skan 1643169689Skan /* These insns only operate on the top of the stack. */ 1644169689Skan 1645169689Skan src1 = get_true_reg (&XVECEXP (pat_src, 0, 0)); 1646169689Skan 1647169689Skan emit_swap_insn (insn, regstack, *src1); 1648169689Skan 1649169689Skan /* Input should never die, it is 1650169689Skan replaced with output. */ 1651169689Skan src1_note = find_regno_note (insn, REG_DEAD, REGNO (*src1)); 1652169689Skan gcc_assert (!src1_note); 1653169689Skan 1654169689Skan if (STACK_REG_P (*dest)) 1655169689Skan replace_reg (dest, FIRST_STACK_REG); 1656169689Skan 1657169689Skan replace_reg (src1, FIRST_STACK_REG); 1658169689Skan break; 1659169689Skan 1660132718Skan case UNSPEC_FPATAN: 1661132718Skan case UNSPEC_FYL2X: 1662169689Skan case UNSPEC_FYL2XP1: 1663132718Skan /* These insns operate on the top two stack slots. */ 1664132718Skan 1665132718Skan src1 = get_true_reg (&XVECEXP (pat_src, 0, 0)); 1666132718Skan src2 = get_true_reg (&XVECEXP (pat_src, 0, 1)); 1667132718Skan 1668132718Skan src1_note = find_regno_note (insn, REG_DEAD, REGNO (*src1)); 1669132718Skan src2_note = find_regno_note (insn, REG_DEAD, REGNO (*src2)); 1670132718Skan 1671169689Skan swap_to_top (insn, regstack, *src1, *src2); 1672132718Skan 1673132718Skan replace_reg (src1, FIRST_STACK_REG); 1674132718Skan replace_reg (src2, FIRST_STACK_REG + 1); 1675132718Skan 1676132718Skan if (src1_note) 1677132718Skan replace_reg (&XEXP (src1_note, 0), FIRST_STACK_REG); 1678132718Skan if (src2_note) 1679132718Skan replace_reg (&XEXP (src2_note, 0), FIRST_STACK_REG + 1); 1680132718Skan 1681132718Skan /* Pop both input operands from the stack. */ 1682132718Skan CLEAR_HARD_REG_BIT (regstack->reg_set, 1683132718Skan regstack->reg[regstack->top]); 1684132718Skan CLEAR_HARD_REG_BIT (regstack->reg_set, 1685132718Skan regstack->reg[regstack->top - 1]); 1686132718Skan regstack->top -= 2; 1687132718Skan 1688132718Skan /* Push the result back onto the stack. */ 1689132718Skan regstack->reg[++regstack->top] = REGNO (*dest); 1690132718Skan SET_HARD_REG_BIT (regstack->reg_set, REGNO (*dest)); 1691132718Skan replace_reg (dest, FIRST_STACK_REG); 1692132718Skan break; 1693132718Skan 1694169689Skan case UNSPEC_FSCALE_FRACT: 1695169689Skan case UNSPEC_FPREM_F: 1696169689Skan case UNSPEC_FPREM1_F: 1697169689Skan /* These insns operate on the top two stack slots. 1698169689Skan first part of double input, double output insn. */ 1699169689Skan 1700169689Skan src1 = get_true_reg (&XVECEXP (pat_src, 0, 0)); 1701169689Skan src2 = get_true_reg (&XVECEXP (pat_src, 0, 1)); 1702169689Skan 1703169689Skan src1_note = find_regno_note (insn, REG_DEAD, REGNO (*src1)); 1704169689Skan src2_note = find_regno_note (insn, REG_DEAD, REGNO (*src2)); 1705169689Skan 1706169689Skan /* Inputs should never die, they are 1707169689Skan replaced with outputs. */ 1708169689Skan gcc_assert (!src1_note); 1709169689Skan gcc_assert (!src2_note); 1710169689Skan 1711169689Skan swap_to_top (insn, regstack, *src1, *src2); 1712169689Skan 1713169689Skan /* Push the result back onto stack. Empty stack slot 1714169689Skan will be filled in second part of insn. */ 1715169689Skan if (STACK_REG_P (*dest)) { 1716169689Skan regstack->reg[regstack->top] = REGNO (*dest); 1717169689Skan SET_HARD_REG_BIT (regstack->reg_set, REGNO (*dest)); 1718169689Skan replace_reg (dest, FIRST_STACK_REG); 1719169689Skan } 1720169689Skan 1721169689Skan replace_reg (src1, FIRST_STACK_REG); 1722169689Skan replace_reg (src2, FIRST_STACK_REG + 1); 1723169689Skan break; 1724169689Skan 1725169689Skan case UNSPEC_FSCALE_EXP: 1726169689Skan case UNSPEC_FPREM_U: 1727169689Skan case UNSPEC_FPREM1_U: 1728169689Skan /* These insns operate on the top two stack slots./ 1729169689Skan second part of double input, double output insn. */ 1730169689Skan 1731169689Skan src1 = get_true_reg (&XVECEXP (pat_src, 0, 0)); 1732169689Skan src2 = get_true_reg (&XVECEXP (pat_src, 0, 1)); 1733169689Skan 1734169689Skan src1_note = find_regno_note (insn, REG_DEAD, REGNO (*src1)); 1735169689Skan src2_note = find_regno_note (insn, REG_DEAD, REGNO (*src2)); 1736169689Skan 1737169689Skan /* Inputs should never die, they are 1738169689Skan replaced with outputs. */ 1739169689Skan gcc_assert (!src1_note); 1740169689Skan gcc_assert (!src2_note); 1741169689Skan 1742169689Skan swap_to_top (insn, regstack, *src1, *src2); 1743169689Skan 1744169689Skan /* Push the result back onto stack. Fill empty slot from 1745169689Skan first part of insn and fix top of stack pointer. */ 1746169689Skan if (STACK_REG_P (*dest)) { 1747169689Skan regstack->reg[regstack->top - 1] = REGNO (*dest); 1748169689Skan SET_HARD_REG_BIT (regstack->reg_set, REGNO (*dest)); 1749169689Skan replace_reg (dest, FIRST_STACK_REG + 1); 1750169689Skan } 1751169689Skan 1752169689Skan replace_reg (src1, FIRST_STACK_REG); 1753169689Skan replace_reg (src2, FIRST_STACK_REG + 1); 1754169689Skan break; 1755169689Skan 1756169689Skan case UNSPEC_SINCOS_COS: 1757169689Skan case UNSPEC_TAN_ONE: 1758169689Skan case UNSPEC_XTRACT_FRACT: 1759169689Skan /* These insns operate on the top two stack slots, 1760169689Skan first part of one input, double output insn. */ 1761169689Skan 1762169689Skan src1 = get_true_reg (&XVECEXP (pat_src, 0, 0)); 1763169689Skan 1764169689Skan emit_swap_insn (insn, regstack, *src1); 1765169689Skan 1766169689Skan /* Input should never die, it is 1767169689Skan replaced with output. */ 1768169689Skan src1_note = find_regno_note (insn, REG_DEAD, REGNO (*src1)); 1769169689Skan gcc_assert (!src1_note); 1770169689Skan 1771169689Skan /* Push the result back onto stack. Empty stack slot 1772169689Skan will be filled in second part of insn. */ 1773169689Skan if (STACK_REG_P (*dest)) { 1774169689Skan regstack->reg[regstack->top + 1] = REGNO (*dest); 1775169689Skan SET_HARD_REG_BIT (regstack->reg_set, REGNO (*dest)); 1776169689Skan replace_reg (dest, FIRST_STACK_REG); 1777169689Skan } 1778169689Skan 1779169689Skan replace_reg (src1, FIRST_STACK_REG); 1780169689Skan break; 1781169689Skan 1782169689Skan case UNSPEC_SINCOS_SIN: 1783169689Skan case UNSPEC_TAN_TAN: 1784169689Skan case UNSPEC_XTRACT_EXP: 1785169689Skan /* These insns operate on the top two stack slots, 1786169689Skan second part of one input, double output insn. */ 1787169689Skan 1788169689Skan src1 = get_true_reg (&XVECEXP (pat_src, 0, 0)); 1789169689Skan 1790169689Skan emit_swap_insn (insn, regstack, *src1); 1791169689Skan 1792169689Skan /* Input should never die, it is 1793169689Skan replaced with output. */ 1794169689Skan src1_note = find_regno_note (insn, REG_DEAD, REGNO (*src1)); 1795169689Skan gcc_assert (!src1_note); 1796169689Skan 1797169689Skan /* Push the result back onto stack. Fill empty slot from 1798169689Skan first part of insn and fix top of stack pointer. */ 1799169689Skan if (STACK_REG_P (*dest)) { 1800169689Skan regstack->reg[regstack->top] = REGNO (*dest); 1801169689Skan SET_HARD_REG_BIT (regstack->reg_set, REGNO (*dest)); 1802169689Skan replace_reg (dest, FIRST_STACK_REG + 1); 1803169689Skan 1804169689Skan regstack->top++; 1805169689Skan } 1806169689Skan 1807169689Skan replace_reg (src1, FIRST_STACK_REG); 1808169689Skan break; 1809169689Skan 1810117395Skan case UNSPEC_SAHF: 1811117395Skan /* (unspec [(unspec [(compare)] UNSPEC_FNSTSW)] UNSPEC_SAHF) 1812117395Skan The combination matches the PPRO fcomi instruction. */ 181318334Speter 181490075Sobrien pat_src = XVECEXP (pat_src, 0, 0); 1815169689Skan gcc_assert (GET_CODE (pat_src) == UNSPEC); 1816169689Skan gcc_assert (XINT (pat_src, 1) == UNSPEC_FNSTSW); 1817132718Skan /* Fall through. */ 181818334Speter 1819117395Skan case UNSPEC_FNSTSW: 182090075Sobrien /* Combined fcomp+fnstsw generated for doing well with 182190075Sobrien CSE. When optimizing this would have been broken 182290075Sobrien up before now. */ 182318334Speter 182490075Sobrien pat_src = XVECEXP (pat_src, 0, 0); 1825169689Skan gcc_assert (GET_CODE (pat_src) == COMPARE); 182618334Speter 182790075Sobrien compare_for_stack_reg (insn, regstack, pat_src); 182890075Sobrien break; 182918334Speter 183090075Sobrien default: 1831169689Skan gcc_unreachable (); 183290075Sobrien } 183318334Speter break; 183418334Speter 183590075Sobrien case IF_THEN_ELSE: 183690075Sobrien /* This insn requires the top of stack to be the destination. */ 183718334Speter 183890075Sobrien src1 = get_true_reg (&XEXP (pat_src, 1)); 183990075Sobrien src2 = get_true_reg (&XEXP (pat_src, 2)); 184050397Sobrien 184190075Sobrien src1_note = find_regno_note (insn, REG_DEAD, REGNO (*src1)); 184290075Sobrien src2_note = find_regno_note (insn, REG_DEAD, REGNO (*src2)); 184350397Sobrien 184490075Sobrien /* If the comparison operator is an FP comparison operator, 184590075Sobrien it is handled correctly by compare_for_stack_reg () who 184690075Sobrien will move the destination to the top of stack. But if the 184790075Sobrien comparison operator is not an FP comparison operator, we 184890075Sobrien have to handle it here. */ 184990075Sobrien if (get_hard_regnum (regstack, *dest) >= FIRST_STACK_REG 185090075Sobrien && REGNO (*dest) != regstack->reg[regstack->top]) 185190075Sobrien { 185290075Sobrien /* In case one of operands is the top of stack and the operands 1853117395Skan dies, it is safe to make it the destination operand by 1854117395Skan reversing the direction of cmove and avoid fxch. */ 185590075Sobrien if ((REGNO (*src1) == regstack->reg[regstack->top] 185690075Sobrien && src1_note) 185790075Sobrien || (REGNO (*src2) == regstack->reg[regstack->top] 185890075Sobrien && src2_note)) 185990075Sobrien { 186090075Sobrien int idx1 = (get_hard_regnum (regstack, *src1) 186190075Sobrien - FIRST_STACK_REG); 186290075Sobrien int idx2 = (get_hard_regnum (regstack, *src2) 186390075Sobrien - FIRST_STACK_REG); 186450397Sobrien 186590075Sobrien /* Make reg-stack believe that the operands are already 186690075Sobrien swapped on the stack */ 186790075Sobrien regstack->reg[regstack->top - idx1] = REGNO (*src2); 186890075Sobrien regstack->reg[regstack->top - idx2] = REGNO (*src1); 186950397Sobrien 187090075Sobrien /* Reverse condition to compensate the operand swap. 187190075Sobrien i386 do have comparison always reversible. */ 187290075Sobrien PUT_CODE (XEXP (pat_src, 0), 187390075Sobrien reversed_comparison_code (XEXP (pat_src, 0), insn)); 187490075Sobrien } 187590075Sobrien else 1876117395Skan emit_swap_insn (insn, regstack, *dest); 187790075Sobrien } 187850397Sobrien 187990075Sobrien { 188090075Sobrien rtx src_note [3]; 188190075Sobrien int i; 188250397Sobrien 188390075Sobrien src_note[0] = 0; 188490075Sobrien src_note[1] = src1_note; 188590075Sobrien src_note[2] = src2_note; 188650397Sobrien 188790075Sobrien if (STACK_REG_P (*src1)) 188890075Sobrien replace_reg (src1, get_hard_regnum (regstack, *src1)); 188990075Sobrien if (STACK_REG_P (*src2)) 189090075Sobrien replace_reg (src2, get_hard_regnum (regstack, *src2)); 189150397Sobrien 189290075Sobrien for (i = 1; i <= 2; i++) 189390075Sobrien if (src_note [i]) 189450397Sobrien { 189590075Sobrien int regno = REGNO (XEXP (src_note[i], 0)); 189690075Sobrien 189790075Sobrien /* If the register that dies is not at the top of 1898169689Skan stack, then move the top of stack to the dead reg. 1899169689Skan Top of stack should never die, as it is the 1900169689Skan destination. */ 1901169689Skan gcc_assert (regno != regstack->reg[regstack->top]); 1902169689Skan remove_regno_note (insn, REG_DEAD, regno); 1903169689Skan emit_pop_insn (insn, regstack, XEXP (src_note[i], 0), 1904169689Skan EMIT_AFTER); 190550397Sobrien } 190690075Sobrien } 190750397Sobrien 190890075Sobrien /* Make dest the top of stack. Add dest to regstack if 190990075Sobrien not present. */ 191090075Sobrien if (get_hard_regnum (regstack, *dest) < FIRST_STACK_REG) 1911117395Skan regstack->reg[++regstack->top] = REGNO (*dest); 191290075Sobrien SET_HARD_REG_BIT (regstack->reg_set, REGNO (*dest)); 191390075Sobrien replace_reg (dest, FIRST_STACK_REG); 191490075Sobrien break; 191550397Sobrien 191690075Sobrien default: 1917169689Skan gcc_unreachable (); 191890075Sobrien } 191950397Sobrien break; 192090075Sobrien } 192150397Sobrien 192290075Sobrien default: 192390075Sobrien break; 192490075Sobrien } 1925132718Skan 1926132718Skan return control_flow_insn_deleted; 192718334Speter} 192818334Speter 192918334Speter/* Substitute hard regnums for any stack regs in INSN, which has 193018334Speter N_INPUTS inputs and N_OUTPUTS outputs. REGSTACK is the stack info 193152284Sobrien before the insn, and is updated with changes made here. 193218334Speter 193318334Speter There are several requirements and assumptions about the use of 193418334Speter stack-like regs in asm statements. These rules are enforced by 193518334Speter record_asm_stack_regs; see comments there for details. Any 193618334Speter asm_operands left in the RTL at this point may be assume to meet the 193718334Speter requirements, since record_asm_stack_regs removes any problem asm. */ 193818334Speter 193918334Speterstatic void 1940132718Skansubst_asm_stack_regs (rtx insn, stack regstack) 194118334Speter{ 194218334Speter rtx body = PATTERN (insn); 194352284Sobrien int alt; 194418334Speter 194518334Speter rtx *note_reg; /* Array of note contents */ 194618334Speter rtx **note_loc; /* Address of REG field of each note */ 194718334Speter enum reg_note *note_kind; /* The type of each note */ 194818334Speter 194990075Sobrien rtx *clobber_reg = 0; 195090075Sobrien rtx **clobber_loc = 0; 195118334Speter 195218334Speter struct stack_def temp_stack; 195318334Speter int n_notes; 195418334Speter int n_clobbers; 195518334Speter rtx note; 195618334Speter int i; 195752284Sobrien int n_inputs, n_outputs; 195818334Speter 195990075Sobrien if (! check_asm_stack_operands (insn)) 196090075Sobrien return; 196190075Sobrien 196218334Speter /* Find out what the constraints required. If no constraint 196318334Speter alternative matches, that is a compiler bug: we should have caught 196490075Sobrien such an insn in check_asm_stack_operands. */ 196552284Sobrien extract_insn (insn); 196652284Sobrien constrain_operands (1); 196752284Sobrien alt = which_alternative; 196818334Speter 196952284Sobrien preprocess_constraints (); 197052284Sobrien 197152284Sobrien n_inputs = get_asm_operand_n_inputs (body); 197290075Sobrien n_outputs = recog_data.n_operands - n_inputs; 1973117395Skan 1974169689Skan gcc_assert (alt >= 0); 197518334Speter 197650397Sobrien /* Strip SUBREGs here to make the following code simpler. */ 197790075Sobrien for (i = 0; i < recog_data.n_operands; i++) 197890075Sobrien if (GET_CODE (recog_data.operand[i]) == SUBREG 1979169689Skan && REG_P (SUBREG_REG (recog_data.operand[i]))) 198018334Speter { 198190075Sobrien recog_data.operand_loc[i] = & SUBREG_REG (recog_data.operand[i]); 198290075Sobrien recog_data.operand[i] = SUBREG_REG (recog_data.operand[i]); 198318334Speter } 198418334Speter 198518334Speter /* Set up NOTE_REG, NOTE_LOC and NOTE_KIND. */ 198618334Speter 198718334Speter for (i = 0, note = REG_NOTES (insn); note; note = XEXP (note, 1)) 198818334Speter i++; 198918334Speter 1990132718Skan note_reg = alloca (i * sizeof (rtx)); 1991132718Skan note_loc = alloca (i * sizeof (rtx *)); 1992132718Skan note_kind = alloca (i * sizeof (enum reg_note)); 199318334Speter 199418334Speter n_notes = 0; 199518334Speter for (note = REG_NOTES (insn); note; note = XEXP (note, 1)) 199618334Speter { 199718334Speter rtx reg = XEXP (note, 0); 199818334Speter rtx *loc = & XEXP (note, 0); 199918334Speter 2000169689Skan if (GET_CODE (reg) == SUBREG && REG_P (SUBREG_REG (reg))) 200118334Speter { 200218334Speter loc = & SUBREG_REG (reg); 200318334Speter reg = SUBREG_REG (reg); 200418334Speter } 200518334Speter 200618334Speter if (STACK_REG_P (reg) 200718334Speter && (REG_NOTE_KIND (note) == REG_DEAD 200818334Speter || REG_NOTE_KIND (note) == REG_UNUSED)) 200918334Speter { 201018334Speter note_reg[n_notes] = reg; 201118334Speter note_loc[n_notes] = loc; 201218334Speter note_kind[n_notes] = REG_NOTE_KIND (note); 201318334Speter n_notes++; 201418334Speter } 201518334Speter } 201618334Speter 201718334Speter /* Set up CLOBBER_REG and CLOBBER_LOC. */ 201818334Speter 201918334Speter n_clobbers = 0; 202018334Speter 202118334Speter if (GET_CODE (body) == PARALLEL) 202218334Speter { 2023132718Skan clobber_reg = alloca (XVECLEN (body, 0) * sizeof (rtx)); 2024132718Skan clobber_loc = alloca (XVECLEN (body, 0) * sizeof (rtx *)); 202518334Speter 202618334Speter for (i = 0; i < XVECLEN (body, 0); i++) 202718334Speter if (GET_CODE (XVECEXP (body, 0, i)) == CLOBBER) 202818334Speter { 202918334Speter rtx clobber = XVECEXP (body, 0, i); 203018334Speter rtx reg = XEXP (clobber, 0); 203118334Speter rtx *loc = & XEXP (clobber, 0); 203218334Speter 2033169689Skan if (GET_CODE (reg) == SUBREG && REG_P (SUBREG_REG (reg))) 203418334Speter { 203518334Speter loc = & SUBREG_REG (reg); 203618334Speter reg = SUBREG_REG (reg); 203718334Speter } 203818334Speter 203918334Speter if (STACK_REG_P (reg)) 204018334Speter { 204118334Speter clobber_reg[n_clobbers] = reg; 204218334Speter clobber_loc[n_clobbers] = loc; 204318334Speter n_clobbers++; 204418334Speter } 204518334Speter } 204618334Speter } 204718334Speter 204890075Sobrien temp_stack = *regstack; 204918334Speter 205018334Speter /* Put the input regs into the desired place in TEMP_STACK. */ 205118334Speter 205252284Sobrien for (i = n_outputs; i < n_outputs + n_inputs; i++) 205390075Sobrien if (STACK_REG_P (recog_data.operand[i]) 2054169689Skan && reg_class_subset_p (recog_op_alt[i][alt].cl, 205552284Sobrien FLOAT_REGS) 2056169689Skan && recog_op_alt[i][alt].cl != FLOAT_REGS) 205718334Speter { 205818334Speter /* If an operand needs to be in a particular reg in 205918334Speter FLOAT_REGS, the constraint was either 't' or 'u'. Since 206090075Sobrien these constraints are for single register classes, and 206190075Sobrien reload guaranteed that operand[i] is already in that class, 206290075Sobrien we can just use REGNO (recog_data.operand[i]) to know which 206390075Sobrien actual reg this operand needs to be in. */ 206418334Speter 206590075Sobrien int regno = get_hard_regnum (&temp_stack, recog_data.operand[i]); 206618334Speter 2067169689Skan gcc_assert (regno >= 0); 206818334Speter 206990075Sobrien if ((unsigned int) regno != REGNO (recog_data.operand[i])) 207018334Speter { 207190075Sobrien /* recog_data.operand[i] is not in the right place. Find 207290075Sobrien it and swap it with whatever is already in I's place. 207390075Sobrien K is where recog_data.operand[i] is now. J is where it 207490075Sobrien should be. */ 207518334Speter int j, k, temp; 207618334Speter 207718334Speter k = temp_stack.top - (regno - FIRST_STACK_REG); 207818334Speter j = (temp_stack.top 207990075Sobrien - (REGNO (recog_data.operand[i]) - FIRST_STACK_REG)); 208018334Speter 208118334Speter temp = temp_stack.reg[k]; 208218334Speter temp_stack.reg[k] = temp_stack.reg[j]; 208318334Speter temp_stack.reg[j] = temp; 208418334Speter } 208518334Speter } 208618334Speter 208790075Sobrien /* Emit insns before INSN to make sure the reg-stack is in the right 208818334Speter order. */ 208918334Speter 209090075Sobrien change_stack (insn, regstack, &temp_stack, EMIT_BEFORE); 209118334Speter 209218334Speter /* Make the needed input register substitutions. Do death notes and 209350397Sobrien clobbers too, because these are for inputs, not outputs. */ 209418334Speter 209552284Sobrien for (i = n_outputs; i < n_outputs + n_inputs; i++) 209690075Sobrien if (STACK_REG_P (recog_data.operand[i])) 209718334Speter { 209890075Sobrien int regnum = get_hard_regnum (regstack, recog_data.operand[i]); 209918334Speter 2100169689Skan gcc_assert (regnum >= 0); 210118334Speter 210290075Sobrien replace_reg (recog_data.operand_loc[i], regnum); 210318334Speter } 210418334Speter 210518334Speter for (i = 0; i < n_notes; i++) 210618334Speter if (note_kind[i] == REG_DEAD) 210718334Speter { 210818334Speter int regnum = get_hard_regnum (regstack, note_reg[i]); 210918334Speter 2110169689Skan gcc_assert (regnum >= 0); 211118334Speter 211218334Speter replace_reg (note_loc[i], regnum); 211318334Speter } 211418334Speter 211518334Speter for (i = 0; i < n_clobbers; i++) 211618334Speter { 211718334Speter /* It's OK for a CLOBBER to reference a reg that is not live. 211818334Speter Don't try to replace it in that case. */ 211918334Speter int regnum = get_hard_regnum (regstack, clobber_reg[i]); 212018334Speter 212118334Speter if (regnum >= 0) 212218334Speter { 212318334Speter /* Sigh - clobbers always have QImode. But replace_reg knows 2124169689Skan that these regs can't be MODE_INT and will assert. Just put 212518334Speter the right reg there without calling replace_reg. */ 212618334Speter 212718334Speter *clobber_loc[i] = FP_MODE_REG (regnum, DFmode); 212818334Speter } 212918334Speter } 213018334Speter 213150397Sobrien /* Now remove from REGSTACK any inputs that the asm implicitly popped. */ 213218334Speter 213352284Sobrien for (i = n_outputs; i < n_outputs + n_inputs; i++) 213490075Sobrien if (STACK_REG_P (recog_data.operand[i])) 213518334Speter { 213618334Speter /* An input reg is implicitly popped if it is tied to an 213750397Sobrien output, or if there is a CLOBBER for it. */ 213818334Speter int j; 213918334Speter 214018334Speter for (j = 0; j < n_clobbers; j++) 214190075Sobrien if (operands_match_p (clobber_reg[j], recog_data.operand[i])) 214218334Speter break; 214318334Speter 214452284Sobrien if (j < n_clobbers || recog_op_alt[i][alt].matches >= 0) 214518334Speter { 214690075Sobrien /* recog_data.operand[i] might not be at the top of stack. 214790075Sobrien But that's OK, because all we need to do is pop the 214890075Sobrien right number of regs off of the top of the reg-stack. 214990075Sobrien record_asm_stack_regs guaranteed that all implicitly 215090075Sobrien popped regs were grouped at the top of the reg-stack. */ 215118334Speter 215218334Speter CLEAR_HARD_REG_BIT (regstack->reg_set, 215318334Speter regstack->reg[regstack->top]); 215418334Speter regstack->top--; 215518334Speter } 215618334Speter } 215718334Speter 215818334Speter /* Now add to REGSTACK any outputs that the asm implicitly pushed. 215918334Speter Note that there isn't any need to substitute register numbers. 216050397Sobrien ??? Explain why this is true. */ 216118334Speter 216218334Speter for (i = LAST_STACK_REG; i >= FIRST_STACK_REG; i--) 216318334Speter { 216418334Speter /* See if there is an output for this hard reg. */ 216518334Speter int j; 216618334Speter 216718334Speter for (j = 0; j < n_outputs; j++) 216890075Sobrien if (STACK_REG_P (recog_data.operand[j]) 216990075Sobrien && REGNO (recog_data.operand[j]) == (unsigned) i) 217018334Speter { 217118334Speter regstack->reg[++regstack->top] = i; 217218334Speter SET_HARD_REG_BIT (regstack->reg_set, i); 217318334Speter break; 217418334Speter } 217518334Speter } 217618334Speter 217718334Speter /* Now emit a pop insn for any REG_UNUSED output, or any REG_DEAD 217818334Speter input that the asm didn't implicitly pop. If the asm didn't 217918334Speter implicitly pop an input reg, that reg will still be live. 218018334Speter 218118334Speter Note that we can't use find_regno_note here: the register numbers 218218334Speter in the death notes have already been substituted. */ 218318334Speter 218418334Speter for (i = 0; i < n_outputs; i++) 218590075Sobrien if (STACK_REG_P (recog_data.operand[i])) 218618334Speter { 218718334Speter int j; 218818334Speter 218918334Speter for (j = 0; j < n_notes; j++) 219090075Sobrien if (REGNO (recog_data.operand[i]) == REGNO (note_reg[j]) 219118334Speter && note_kind[j] == REG_UNUSED) 219218334Speter { 219390075Sobrien insn = emit_pop_insn (insn, regstack, recog_data.operand[i], 219490075Sobrien EMIT_AFTER); 219518334Speter break; 219618334Speter } 219718334Speter } 219818334Speter 219952284Sobrien for (i = n_outputs; i < n_outputs + n_inputs; i++) 220090075Sobrien if (STACK_REG_P (recog_data.operand[i])) 220118334Speter { 220218334Speter int j; 220318334Speter 220418334Speter for (j = 0; j < n_notes; j++) 220590075Sobrien if (REGNO (recog_data.operand[i]) == REGNO (note_reg[j]) 220618334Speter && note_kind[j] == REG_DEAD 220752284Sobrien && TEST_HARD_REG_BIT (regstack->reg_set, 220890075Sobrien REGNO (recog_data.operand[i]))) 220918334Speter { 221090075Sobrien insn = emit_pop_insn (insn, regstack, recog_data.operand[i], 221190075Sobrien EMIT_AFTER); 221218334Speter break; 221318334Speter } 221418334Speter } 221518334Speter} 221618334Speter 221718334Speter/* Substitute stack hard reg numbers for stack virtual registers in 221818334Speter INSN. Non-stack register numbers are not changed. REGSTACK is the 221918334Speter current stack content. Insns may be emitted as needed to arrange the 2220132718Skan stack for the 387 based on the contents of the insn. Return whether 2221132718Skan a control flow insn was deleted in the process. */ 222218334Speter 2223132718Skanstatic bool 2224132718Skansubst_stack_regs (rtx insn, stack regstack) 222518334Speter{ 222690075Sobrien rtx *note_link, note; 2227132718Skan bool control_flow_insn_deleted = false; 222890075Sobrien int i; 222918334Speter 2230169689Skan if (CALL_P (insn)) 223190075Sobrien { 223290075Sobrien int top = regstack->top; 223318334Speter 223490075Sobrien /* If there are any floating point parameters to be passed in 223590075Sobrien registers for this call, make sure they are in the right 223690075Sobrien order. */ 223718334Speter 223890075Sobrien if (top >= 0) 223990075Sobrien { 2240169689Skan straighten_stack (insn, regstack); 224118334Speter 224290075Sobrien /* Now mark the arguments as dead after the call. */ 224318334Speter 224490075Sobrien while (regstack->top >= 0) 224590075Sobrien { 224690075Sobrien CLEAR_HARD_REG_BIT (regstack->reg_set, FIRST_STACK_REG + regstack->top); 224790075Sobrien regstack->top--; 224890075Sobrien } 224990075Sobrien } 225090075Sobrien } 225118334Speter 225218334Speter /* Do the actual substitution if any stack regs are mentioned. 225318334Speter Since we only record whether entire insn mentions stack regs, and 225418334Speter subst_stack_regs_pat only works for patterns that contain stack regs, 225518334Speter we must check each pattern in a parallel here. A call_value_pop could 225650397Sobrien fail otherwise. */ 225718334Speter 225852284Sobrien if (stack_regs_mentioned (insn)) 225918334Speter { 226052284Sobrien int n_operands = asm_noperands (PATTERN (insn)); 226118334Speter if (n_operands >= 0) 226218334Speter { 226318334Speter /* This insn is an `asm' with operands. Decode the operands, 226418334Speter decide how many are inputs, and do register substitution. 226550397Sobrien Any REG_UNUSED notes will be handled by subst_asm_stack_regs. */ 226618334Speter 226752284Sobrien subst_asm_stack_regs (insn, regstack); 2268132718Skan return control_flow_insn_deleted; 226918334Speter } 227018334Speter 227118334Speter if (GET_CODE (PATTERN (insn)) == PARALLEL) 227218334Speter for (i = 0; i < XVECLEN (PATTERN (insn), 0); i++) 227318334Speter { 227418334Speter if (stack_regs_mentioned_p (XVECEXP (PATTERN (insn), 0, i))) 2275169689Skan { 2276169689Skan if (GET_CODE (XVECEXP (PATTERN (insn), 0, i)) == CLOBBER) 2277169689Skan XVECEXP (PATTERN (insn), 0, i) 2278169689Skan = shallow_copy_rtx (XVECEXP (PATTERN (insn), 0, i)); 2279169689Skan control_flow_insn_deleted 2280169689Skan |= subst_stack_regs_pat (insn, regstack, 2281169689Skan XVECEXP (PATTERN (insn), 0, i)); 2282169689Skan } 228318334Speter } 228418334Speter else 2285132718Skan control_flow_insn_deleted 2286132718Skan |= subst_stack_regs_pat (insn, regstack, PATTERN (insn)); 228718334Speter } 228818334Speter 228918334Speter /* subst_stack_regs_pat may have deleted a no-op insn. If so, any 229050397Sobrien REG_UNUSED will already have been dealt with, so just return. */ 229118334Speter 2292169689Skan if (NOTE_P (insn) || INSN_DELETED_P (insn)) 2293132718Skan return control_flow_insn_deleted; 229418334Speter 2295169689Skan /* If this a noreturn call, we can't insert pop insns after it. 2296169689Skan Instead, reset the stack state to empty. */ 2297169689Skan if (CALL_P (insn) 2298169689Skan && find_reg_note (insn, REG_NORETURN, NULL)) 2299169689Skan { 2300169689Skan regstack->top = -1; 2301169689Skan CLEAR_HARD_REG_SET (regstack->reg_set); 2302169689Skan return control_flow_insn_deleted; 2303169689Skan } 2304169689Skan 230518334Speter /* If there is a REG_UNUSED note on a stack register on this insn, 230618334Speter the indicated reg must be popped. The REG_UNUSED note is removed, 230718334Speter since the form of the newly emitted pop insn references the reg, 230850397Sobrien making it no longer `unset'. */ 230918334Speter 231090075Sobrien note_link = ®_NOTES (insn); 231118334Speter for (note = *note_link; note; note = XEXP (note, 1)) 231218334Speter if (REG_NOTE_KIND (note) == REG_UNUSED && STACK_REG_P (XEXP (note, 0))) 231318334Speter { 231418334Speter *note_link = XEXP (note, 1); 231590075Sobrien insn = emit_pop_insn (insn, regstack, XEXP (note, 0), EMIT_AFTER); 231618334Speter } 231718334Speter else 231818334Speter note_link = &XEXP (note, 1); 2319132718Skan 2320132718Skan return control_flow_insn_deleted; 232118334Speter} 232218334Speter 232318334Speter/* Change the organization of the stack so that it fits a new basic 232418334Speter block. Some registers might have to be popped, but there can never be 232518334Speter a register live in the new block that is not now live. 232618334Speter 232790075Sobrien Insert any needed insns before or after INSN, as indicated by 232890075Sobrien WHERE. OLD is the original stack layout, and NEW is the desired 2329169689Skan form. OLD is updated to reflect the code emitted, i.e., it will be 233090075Sobrien the same as NEW upon return. 233118334Speter 233218334Speter This function will not preserve block_end[]. But that information 233350397Sobrien is no longer needed once this has executed. */ 233418334Speter 233518334Speterstatic void 2336132718Skanchange_stack (rtx insn, stack old, stack new, enum emit_where where) 233718334Speter{ 233818334Speter int reg; 233990075Sobrien int update_end = 0; 234018334Speter 2341169689Skan /* Stack adjustments for the first insn in a block update the 2342169689Skan current_block's stack_in instead of inserting insns directly. 2343169689Skan compensate_edges will add the necessary code later. */ 2344169689Skan if (current_block 2345169689Skan && starting_stack_p 2346169689Skan && where == EMIT_BEFORE) 2347169689Skan { 2348169689Skan BLOCK_INFO (current_block)->stack_in = *new; 2349169689Skan starting_stack_p = false; 2350169689Skan *old = *new; 2351169689Skan return; 2352169689Skan } 2353169689Skan 235490075Sobrien /* We will be inserting new insns "backwards". If we are to insert 235590075Sobrien after INSN, find the next insn, and insert before it. */ 235618334Speter 235790075Sobrien if (where == EMIT_AFTER) 235890075Sobrien { 2359132718Skan if (current_block && BB_END (current_block) == insn) 236090075Sobrien update_end = 1; 236190075Sobrien insn = NEXT_INSN (insn); 236290075Sobrien } 236318334Speter 236450397Sobrien /* Pop any registers that are not needed in the new block. */ 236518334Speter 2366169689Skan /* If the destination block's stack already has a specified layout 2367169689Skan and contains two or more registers, use a more intelligent algorithm 2368169689Skan to pop registers that minimizes the number number of fxchs below. */ 2369169689Skan if (new->top > 0) 2370169689Skan { 2371169689Skan bool slots[REG_STACK_SIZE]; 2372169689Skan int pops[REG_STACK_SIZE]; 2373169689Skan int next, dest, topsrc; 237418334Speter 2375169689Skan /* First pass to determine the free slots. */ 2376169689Skan for (reg = 0; reg <= new->top; reg++) 2377169689Skan slots[reg] = TEST_HARD_REG_BIT (new->reg_set, old->reg[reg]); 2378169689Skan 2379169689Skan /* Second pass to allocate preferred slots. */ 2380169689Skan topsrc = -1; 2381169689Skan for (reg = old->top; reg > new->top; reg--) 2382169689Skan if (TEST_HARD_REG_BIT (new->reg_set, old->reg[reg])) 2383169689Skan { 2384169689Skan dest = -1; 2385169689Skan for (next = 0; next <= new->top; next++) 2386169689Skan if (!slots[next] && new->reg[next] == old->reg[reg]) 2387169689Skan { 2388169689Skan /* If this is a preference for the new top of stack, record 2389169689Skan the fact by remembering it's old->reg in topsrc. */ 2390169689Skan if (next == new->top) 2391169689Skan topsrc = reg; 2392169689Skan slots[next] = true; 2393169689Skan dest = next; 2394169689Skan break; 2395169689Skan } 2396169689Skan pops[reg] = dest; 2397169689Skan } 2398169689Skan else 2399169689Skan pops[reg] = reg; 2400169689Skan 2401169689Skan /* Intentionally, avoid placing the top of stack in it's correct 2402169689Skan location, if we still need to permute the stack below and we 2403169689Skan can usefully place it somewhere else. This is the case if any 2404169689Skan slot is still unallocated, in which case we should place the 2405169689Skan top of stack there. */ 2406169689Skan if (topsrc != -1) 2407169689Skan for (reg = 0; reg < new->top; reg++) 2408169689Skan if (!slots[reg]) 2409169689Skan { 2410169689Skan pops[topsrc] = reg; 2411169689Skan slots[new->top] = false; 2412169689Skan slots[reg] = true; 2413169689Skan break; 2414169689Skan } 2415169689Skan 2416169689Skan /* Third pass allocates remaining slots and emits pop insns. */ 2417169689Skan next = new->top; 2418169689Skan for (reg = old->top; reg > new->top; reg--) 2419169689Skan { 2420169689Skan dest = pops[reg]; 2421169689Skan if (dest == -1) 2422169689Skan { 2423169689Skan /* Find next free slot. */ 2424169689Skan while (slots[next]) 2425169689Skan next--; 2426169689Skan dest = next--; 2427169689Skan } 2428169689Skan emit_pop_insn (insn, old, FP_MODE_REG (old->reg[dest], DFmode), 2429169689Skan EMIT_BEFORE); 2430169689Skan } 2431169689Skan } 2432169689Skan else 2433169689Skan { 2434169689Skan /* The following loop attempts to maximize the number of times we 2435169689Skan pop the top of the stack, as this permits the use of the faster 2436169689Skan ffreep instruction on platforms that support it. */ 2437169689Skan int live, next; 2438169689Skan 2439169689Skan live = 0; 2440169689Skan for (reg = 0; reg <= old->top; reg++) 2441169689Skan if (TEST_HARD_REG_BIT (new->reg_set, old->reg[reg])) 2442169689Skan live++; 2443169689Skan 2444169689Skan next = live; 2445169689Skan while (old->top >= live) 2446169689Skan if (TEST_HARD_REG_BIT (new->reg_set, old->reg[old->top])) 2447169689Skan { 2448169689Skan while (TEST_HARD_REG_BIT (new->reg_set, old->reg[next])) 2449169689Skan next--; 2450169689Skan emit_pop_insn (insn, old, FP_MODE_REG (old->reg[next], DFmode), 2451169689Skan EMIT_BEFORE); 2452169689Skan } 2453169689Skan else 2454169689Skan emit_pop_insn (insn, old, FP_MODE_REG (old->reg[old->top], DFmode), 2455169689Skan EMIT_BEFORE); 2456169689Skan } 2457169689Skan 245818334Speter if (new->top == -2) 245918334Speter { 246018334Speter /* If the new block has never been processed, then it can inherit 246150397Sobrien the old stack order. */ 246218334Speter 246318334Speter new->top = old->top; 246490075Sobrien memcpy (new->reg, old->reg, sizeof (new->reg)); 246518334Speter } 246618334Speter else 246718334Speter { 246818334Speter /* This block has been entered before, and we must match the 246950397Sobrien previously selected stack order. */ 247018334Speter 247118334Speter /* By now, the only difference should be the order of the stack, 247250397Sobrien not their depth or liveliness. */ 247318334Speter 247418334Speter GO_IF_HARD_REG_EQUAL (old->reg_set, new->reg_set, win); 2475169689Skan gcc_unreachable (); 247618334Speter win: 2477169689Skan gcc_assert (old->top == new->top); 247818334Speter 247952284Sobrien /* If the stack is not empty (new->top != -1), loop here emitting 2480117395Skan swaps until the stack is correct. 248152284Sobrien 248252284Sobrien The worst case number of swaps emitted is N + 2, where N is the 248318334Speter depth of the stack. In some cases, the reg at the top of 248418334Speter stack may be correct, but swapped anyway in order to fix 248518334Speter other regs. But since we never swap any other reg away from 248650397Sobrien its correct slot, this algorithm will converge. */ 248718334Speter 248852284Sobrien if (new->top != -1) 248952284Sobrien do 249052284Sobrien { 249152284Sobrien /* Swap the reg at top of stack into the position it is 249252284Sobrien supposed to be in, until the correct top of stack appears. */ 249318334Speter 249452284Sobrien while (old->reg[old->top] != new->reg[new->top]) 249552284Sobrien { 249652284Sobrien for (reg = new->top; reg >= 0; reg--) 249752284Sobrien if (new->reg[reg] == old->reg[old->top]) 249852284Sobrien break; 249918334Speter 2500169689Skan gcc_assert (reg != -1); 250118334Speter 250252284Sobrien emit_swap_insn (insn, old, 250352284Sobrien FP_MODE_REG (old->reg[reg], DFmode)); 250452284Sobrien } 250518334Speter 250652284Sobrien /* See if any regs remain incorrect. If so, bring an 250718334Speter incorrect reg to the top of stack, and let the while loop 250850397Sobrien above fix it. */ 250918334Speter 251052284Sobrien for (reg = new->top; reg >= 0; reg--) 251152284Sobrien if (new->reg[reg] != old->reg[reg]) 251252284Sobrien { 251352284Sobrien emit_swap_insn (insn, old, 251452284Sobrien FP_MODE_REG (old->reg[reg], DFmode)); 251552284Sobrien break; 251652284Sobrien } 251752284Sobrien } while (reg >= 0); 251818334Speter 251950397Sobrien /* At this point there must be no differences. */ 252018334Speter 252118334Speter for (reg = old->top; reg >= 0; reg--) 2522169689Skan gcc_assert (old->reg[reg] == new->reg[reg]); 252318334Speter } 252490075Sobrien 252590075Sobrien if (update_end) 2526132718Skan BB_END (current_block) = PREV_INSN (insn); 252718334Speter} 252818334Speter 252990075Sobrien/* Print stack configuration. */ 253018334Speter 253118334Speterstatic void 2532132718Skanprint_stack (FILE *file, stack s) 253318334Speter{ 253490075Sobrien if (! file) 253590075Sobrien return; 253618334Speter 253790075Sobrien if (s->top == -2) 253890075Sobrien fprintf (file, "uninitialized\n"); 253990075Sobrien else if (s->top == -1) 254090075Sobrien fprintf (file, "empty\n"); 254190075Sobrien else 254290075Sobrien { 254390075Sobrien int i; 254490075Sobrien fputs ("[ ", file); 254590075Sobrien for (i = 0; i <= s->top; ++i) 254690075Sobrien fprintf (file, "%d ", s->reg[i]); 254790075Sobrien fputs ("]\n", file); 254890075Sobrien } 254990075Sobrien} 255090075Sobrien 255190075Sobrien/* This function was doing life analysis. We now let the regular live 2552117395Skan code do it's job, so we only need to check some extra invariants 255390075Sobrien that reg-stack expects. Primary among these being that all registers 255490075Sobrien are initialized before use. 255518334Speter 255690075Sobrien The function returns true when code was emitted to CFG edges and 255790075Sobrien commit_edge_insertions needs to be called. */ 255890075Sobrien 255990075Sobrienstatic int 2560132718Skanconvert_regs_entry (void) 256190075Sobrien{ 2562117395Skan int inserted = 0; 256390075Sobrien edge e; 2564169689Skan edge_iterator ei; 256590075Sobrien 2566117395Skan /* Load something into each stack register live at function entry. 256790075Sobrien Such live registers can be caused by uninitialized variables or 2568117395Skan functions not returning values on all paths. In order to keep 256990075Sobrien the push/pop code happy, and to not scrog the register stack, we 2570117395Skan must put something in these registers. Use a QNaN. 257118334Speter 2572132718Skan Note that we are inserting converted code here. This code is 257390075Sobrien never seen by the convert_regs pass. */ 257418334Speter 2575169689Skan FOR_EACH_EDGE (e, ei, ENTRY_BLOCK_PTR->succs) 257690075Sobrien { 257790075Sobrien basic_block block = e->dest; 257890075Sobrien block_info bi = BLOCK_INFO (block); 257990075Sobrien int reg, top = -1; 258018334Speter 258190075Sobrien for (reg = LAST_STACK_REG; reg >= FIRST_STACK_REG; --reg) 258290075Sobrien if (TEST_HARD_REG_BIT (bi->stack_in.reg_set, reg)) 258390075Sobrien { 258490075Sobrien rtx init; 258590075Sobrien 258690075Sobrien bi->stack_in.reg[++top] = reg; 258790075Sobrien 258890075Sobrien init = gen_rtx_SET (VOIDmode, 258990075Sobrien FP_MODE_REG (FIRST_STACK_REG, SFmode), 2590169689Skan not_a_num); 259190075Sobrien insert_insn_on_edge (init, e); 259290075Sobrien inserted = 1; 259390075Sobrien } 259490075Sobrien 259590075Sobrien bi->stack_in.top = top; 259690075Sobrien } 259790075Sobrien 259890075Sobrien return inserted; 259990075Sobrien} 260090075Sobrien 260190075Sobrien/* Construct the desired stack for function exit. This will either 260290075Sobrien be `empty', or the function return value at top-of-stack. */ 260390075Sobrien 260490075Sobrienstatic void 2605132718Skanconvert_regs_exit (void) 260690075Sobrien{ 260790075Sobrien int value_reg_low, value_reg_high; 260890075Sobrien stack output_stack; 260990075Sobrien rtx retvalue; 261090075Sobrien 261190075Sobrien retvalue = stack_result (current_function_decl); 261290075Sobrien value_reg_low = value_reg_high = -1; 261390075Sobrien if (retvalue) 261418334Speter { 261590075Sobrien value_reg_low = REGNO (retvalue); 261690075Sobrien value_reg_high = value_reg_low 2617169689Skan + hard_regno_nregs[value_reg_low][GET_MODE (retvalue)] - 1; 261890075Sobrien } 261918334Speter 262090075Sobrien output_stack = &BLOCK_INFO (EXIT_BLOCK_PTR)->stack_in; 262190075Sobrien if (value_reg_low == -1) 262290075Sobrien output_stack->top = -1; 262390075Sobrien else 262490075Sobrien { 262590075Sobrien int reg; 262690075Sobrien 262790075Sobrien output_stack->top = value_reg_high - value_reg_low; 262890075Sobrien for (reg = value_reg_low; reg <= value_reg_high; ++reg) 262990075Sobrien { 2630102780Skan output_stack->reg[value_reg_high - reg] = reg; 263190075Sobrien SET_HARD_REG_BIT (output_stack->reg_set, reg); 263290075Sobrien } 263390075Sobrien } 263490075Sobrien} 263590075Sobrien 2636169689Skan/* Copy the stack info from the end of edge E's source block to the 2637169689Skan start of E's destination block. */ 2638169689Skan 2639169689Skanstatic void 2640169689Skanpropagate_stack (edge e) 2641169689Skan{ 2642169689Skan stack src_stack = &BLOCK_INFO (e->src)->stack_out; 2643169689Skan stack dest_stack = &BLOCK_INFO (e->dest)->stack_in; 2644169689Skan int reg; 2645169689Skan 2646169689Skan /* Preserve the order of the original stack, but check whether 2647169689Skan any pops are needed. */ 2648169689Skan dest_stack->top = -1; 2649169689Skan for (reg = 0; reg <= src_stack->top; ++reg) 2650169689Skan if (TEST_HARD_REG_BIT (dest_stack->reg_set, src_stack->reg[reg])) 2651169689Skan dest_stack->reg[++dest_stack->top] = src_stack->reg[reg]; 2652169689Skan} 2653169689Skan 2654169689Skan 2655169689Skan/* Adjust the stack of edge E's source block on exit to match the stack 2656169689Skan of it's target block upon input. The stack layouts of both blocks 2657169689Skan should have been defined by now. */ 2658169689Skan 265990075Sobrienstatic bool 2660169689Skancompensate_edge (edge e) 266190075Sobrien{ 2662169689Skan basic_block source = e->src, target = e->dest; 266390075Sobrien stack target_stack = &BLOCK_INFO (target)->stack_in; 2664169689Skan stack source_stack = &BLOCK_INFO (source)->stack_out; 2665169689Skan struct stack_def regstack; 266690075Sobrien int reg; 266790075Sobrien 2668169689Skan if (dump_file) 2669169689Skan fprintf (dump_file, "Edge %d->%d: ", source->index, target->index); 267090075Sobrien 2671169689Skan gcc_assert (target_stack->top != -2); 2672169689Skan 2673169689Skan /* Check whether stacks are identical. */ 2674169689Skan if (target_stack->top == source_stack->top) 267590075Sobrien { 2676169689Skan for (reg = target_stack->top; reg >= 0; --reg) 2677169689Skan if (target_stack->reg[reg] != source_stack->reg[reg]) 267818334Speter break; 267918334Speter 268018334Speter if (reg == -1) 268118334Speter { 2682169689Skan if (dump_file) 2683169689Skan fprintf (dump_file, "no changes needed\n"); 2684117395Skan return false; 268518334Speter } 2686169689Skan } 268790075Sobrien 2688169689Skan if (dump_file) 268918334Speter { 2690169689Skan fprintf (dump_file, "correcting stack to "); 2691169689Skan print_stack (dump_file, target_stack); 269218334Speter } 269318334Speter 2694169689Skan /* Abnormal calls may appear to have values live in st(0), but the 269590075Sobrien abnormal return path will not have actually loaded the values. */ 2696169689Skan if (e->flags & EDGE_ABNORMAL_CALL) 269790075Sobrien { 269890075Sobrien /* Assert that the lifetimes are as we expect -- one value 269990075Sobrien live at st(0) on the end of the source block, and no 2700169689Skan values live at the beginning of the destination block. 2701117395Skan For complex return values, we may have st(1) live as well. */ 2702169689Skan gcc_assert (source_stack->top == 0 || source_stack->top == 1); 2703169689Skan gcc_assert (target_stack->top == -1); 2704169689Skan return false; 2705169689Skan } 270618334Speter 2707169689Skan /* Handle non-call EH edges specially. The normal return path have 2708169689Skan values in registers. These will be popped en masse by the unwind 2709169689Skan library. */ 2710169689Skan if (e->flags & EDGE_EH) 2711169689Skan { 2712169689Skan gcc_assert (target_stack->top == -1); 2713169689Skan return false; 271490075Sobrien } 271518334Speter 2716169689Skan /* We don't support abnormal edges. Global takes care to 2717169689Skan avoid any live register across them, so we should never 2718169689Skan have to insert instructions on such edges. */ 2719169689Skan gcc_assert (! (e->flags & EDGE_ABNORMAL)); 2720169689Skan 2721169689Skan /* Make a copy of source_stack as change_stack is destructive. */ 2722169689Skan regstack = *source_stack; 2723169689Skan 272490075Sobrien /* It is better to output directly to the end of the block 272590075Sobrien instead of to the edge, because emit_swap can do minimal 272690075Sobrien insn scheduling. We can do this when there is only one 272790075Sobrien edge out, and it is not abnormal. */ 2728169689Skan if (EDGE_COUNT (source->succs) == 1) 272990075Sobrien { 2730169689Skan current_block = source; 2731169689Skan change_stack (BB_END (source), ®stack, target_stack, 2732169689Skan (JUMP_P (BB_END (source)) ? EMIT_BEFORE : EMIT_AFTER)); 273390075Sobrien } 273490075Sobrien else 273590075Sobrien { 273690075Sobrien rtx seq, after; 273718334Speter 273890075Sobrien current_block = NULL; 273990075Sobrien start_sequence (); 274018334Speter 2741117395Skan /* ??? change_stack needs some point to emit insns after. */ 2742132718Skan after = emit_note (NOTE_INSN_DELETED); 274318334Speter 2744169689Skan change_stack (after, ®stack, target_stack, EMIT_BEFORE); 274518334Speter 2746117395Skan seq = get_insns (); 274790075Sobrien end_sequence (); 274818334Speter 274990075Sobrien insert_insn_on_edge (seq, e); 275090075Sobrien return true; 275190075Sobrien } 275290075Sobrien return false; 275318334Speter} 275418334Speter 2755169689Skan/* Traverse all non-entry edges in the CFG, and emit the necessary 2756169689Skan edge compensation code to change the stack from stack_out of the 2757169689Skan source block to the stack_in of the destination block. */ 2758169689Skan 2759169689Skanstatic bool 2760169689Skancompensate_edges (void) 2761169689Skan{ 2762169689Skan bool inserted = false; 2763169689Skan basic_block bb; 2764169689Skan 2765169689Skan starting_stack_p = false; 2766169689Skan 2767169689Skan FOR_EACH_BB (bb) 2768169689Skan if (bb != ENTRY_BLOCK_PTR) 2769169689Skan { 2770169689Skan edge e; 2771169689Skan edge_iterator ei; 2772169689Skan 2773169689Skan FOR_EACH_EDGE (e, ei, bb->succs) 2774169689Skan inserted |= compensate_edge (e); 2775169689Skan } 2776169689Skan return inserted; 2777169689Skan} 2778169689Skan 2779169689Skan/* Select the better of two edges E1 and E2 to use to determine the 2780169689Skan stack layout for their shared destination basic block. This is 2781169689Skan typically the more frequently executed. The edge E1 may be NULL 2782169689Skan (in which case E2 is returned), but E2 is always non-NULL. */ 2783169689Skan 2784169689Skanstatic edge 2785169689Skanbetter_edge (edge e1, edge e2) 2786169689Skan{ 2787169689Skan if (!e1) 2788169689Skan return e2; 2789169689Skan 2790169689Skan if (EDGE_FREQUENCY (e1) > EDGE_FREQUENCY (e2)) 2791169689Skan return e1; 2792169689Skan if (EDGE_FREQUENCY (e1) < EDGE_FREQUENCY (e2)) 2793169689Skan return e2; 2794169689Skan 2795169689Skan if (e1->count > e2->count) 2796169689Skan return e1; 2797169689Skan if (e1->count < e2->count) 2798169689Skan return e2; 2799169689Skan 2800169689Skan /* Prefer critical edges to minimize inserting compensation code on 2801169689Skan critical edges. */ 2802169689Skan 2803169689Skan if (EDGE_CRITICAL_P (e1) != EDGE_CRITICAL_P (e2)) 2804169689Skan return EDGE_CRITICAL_P (e1) ? e1 : e2; 2805169689Skan 2806169689Skan /* Avoid non-deterministic behavior. */ 2807169689Skan return (e1->src->index < e2->src->index) ? e1 : e2; 2808169689Skan} 2809169689Skan 281090075Sobrien/* Convert stack register references in one block. */ 281190075Sobrien 2812169689Skanstatic void 2813169689Skanconvert_regs_1 (basic_block block) 281418334Speter{ 281518334Speter struct stack_def regstack; 281690075Sobrien block_info bi = BLOCK_INFO (block); 2817169689Skan int reg; 281890075Sobrien rtx insn, next; 2819132718Skan bool control_flow_insn_deleted = false; 282018334Speter 2821117395Skan any_malformed_asm = false; 282290075Sobrien 2823169689Skan /* Choose an initial stack layout, if one hasn't already been chosen. */ 2824169689Skan if (bi->stack_in.top == -2) 282518334Speter { 2826169689Skan edge e, beste = NULL; 2827169689Skan edge_iterator ei; 282818334Speter 2829169689Skan /* Select the best incoming edge (typically the most frequent) to 2830169689Skan use as a template for this basic block. */ 2831169689Skan FOR_EACH_EDGE (e, ei, block->preds) 2832169689Skan if (BLOCK_INFO (e->src)->done) 2833169689Skan beste = better_edge (beste, e); 2834169689Skan 2835122180Skan if (beste) 2836169689Skan propagate_stack (beste); 2837122180Skan else 2838122180Skan { 2839122180Skan /* No predecessors. Create an arbitrary input stack. */ 2840122180Skan bi->stack_in.top = -1; 2841122180Skan for (reg = LAST_STACK_REG; reg >= FIRST_STACK_REG; --reg) 2842122180Skan if (TEST_HARD_REG_BIT (bi->stack_in.reg_set, reg)) 2843122180Skan bi->stack_in.reg[++bi->stack_in.top] = reg; 2844122180Skan } 2845122180Skan } 2846117395Skan 2847169689Skan if (dump_file) 284890075Sobrien { 2849169689Skan fprintf (dump_file, "\nBasic block %d\nInput stack: ", block->index); 2850169689Skan print_stack (dump_file, &bi->stack_in); 285190075Sobrien } 285218334Speter 285390075Sobrien /* Process all insns in this block. Keep track of NEXT so that we 285490075Sobrien don't process insns emitted while substituting in INSN. */ 2855169689Skan current_block = block; 2856132718Skan next = BB_HEAD (block); 285790075Sobrien regstack = bi->stack_in; 2858169689Skan starting_stack_p = true; 2859169689Skan 286090075Sobrien do 286190075Sobrien { 286290075Sobrien insn = next; 286390075Sobrien next = NEXT_INSN (insn); 286418334Speter 286590075Sobrien /* Ensure we have not missed a block boundary. */ 2866169689Skan gcc_assert (next); 2867132718Skan if (insn == BB_END (block)) 286890075Sobrien next = NULL; 286918334Speter 287090075Sobrien /* Don't bother processing unless there is a stack reg 287190075Sobrien mentioned or if it's a CALL_INSN. */ 287290075Sobrien if (stack_regs_mentioned (insn) 2873169689Skan || CALL_P (insn)) 287490075Sobrien { 2875169689Skan if (dump_file) 287690075Sobrien { 2877169689Skan fprintf (dump_file, " insn %d input stack: ", 287890075Sobrien INSN_UID (insn)); 2879169689Skan print_stack (dump_file, ®stack); 288090075Sobrien } 2881132718Skan control_flow_insn_deleted |= subst_stack_regs (insn, ®stack); 2882169689Skan starting_stack_p = false; 288390075Sobrien } 288490075Sobrien } 288590075Sobrien while (next); 288650397Sobrien 2887169689Skan if (dump_file) 288890075Sobrien { 2889169689Skan fprintf (dump_file, "Expected live registers ["); 289090075Sobrien for (reg = FIRST_STACK_REG; reg <= LAST_STACK_REG; ++reg) 289190075Sobrien if (TEST_HARD_REG_BIT (bi->out_reg_set, reg)) 2892169689Skan fprintf (dump_file, " %d", reg); 2893169689Skan fprintf (dump_file, " ]\nOutput stack: "); 2894169689Skan print_stack (dump_file, ®stack); 289590075Sobrien } 289618334Speter 2897132718Skan insn = BB_END (block); 2898169689Skan if (JUMP_P (insn)) 289990075Sobrien insn = PREV_INSN (insn); 290018334Speter 290190075Sobrien /* If the function is declared to return a value, but it returns one 290290075Sobrien in only some cases, some registers might come live here. Emit 290390075Sobrien necessary moves for them. */ 290418334Speter 290590075Sobrien for (reg = FIRST_STACK_REG; reg <= LAST_STACK_REG; ++reg) 290690075Sobrien { 290790075Sobrien if (TEST_HARD_REG_BIT (bi->out_reg_set, reg) 290890075Sobrien && ! TEST_HARD_REG_BIT (regstack.reg_set, reg)) 290990075Sobrien { 291090075Sobrien rtx set; 291118334Speter 2912169689Skan if (dump_file) 2913169689Skan fprintf (dump_file, "Emitting insn initializing reg %d\n", reg); 291418334Speter 2915169689Skan set = gen_rtx_SET (VOIDmode, FP_MODE_REG (reg, SFmode), not_a_num); 291690075Sobrien insn = emit_insn_after (set, insn); 2917132718Skan control_flow_insn_deleted |= subst_stack_regs (insn, ®stack); 291890075Sobrien } 291918334Speter } 2920122180Skan 2921122180Skan /* Amongst the insns possibly deleted during the substitution process above, 2922122180Skan might have been the only trapping insn in the block. We purge the now 2923122180Skan possibly dead EH edges here to avoid an ICE from fixup_abnormal_edges, 2924122180Skan called at the end of convert_regs. The order in which we process the 2925122180Skan blocks ensures that we never delete an already processed edge. 292618334Speter 2927132718Skan Note that, at this point, the CFG may have been damaged by the emission 2928132718Skan of instructions after an abnormal call, which moves the basic block end 2929132718Skan (and is the reason why we call fixup_abnormal_edges later). So we must 2930132718Skan be sure that the trapping insn has been deleted before trying to purge 2931132718Skan dead edges, otherwise we risk purging valid edges. 2932132718Skan 2933122180Skan ??? We are normally supposed not to delete trapping insns, so we pretend 2934122180Skan that the insns deleted above don't actually trap. It would have been 2935122180Skan better to detect this earlier and avoid creating the EH edge in the first 2936122180Skan place, still, but we don't have enough information at that time. */ 2937122180Skan 2938132718Skan if (control_flow_insn_deleted) 2939122180Skan purge_dead_edges (block); 2940122180Skan 2941117395Skan /* Something failed if the stack lives don't match. If we had malformed 2942117395Skan asms, we zapped the instruction itself, but that didn't produce the 2943117395Skan same pattern of register kills as before. */ 294490075Sobrien GO_IF_HARD_REG_EQUAL (regstack.reg_set, bi->out_reg_set, win); 2945169689Skan gcc_assert (any_malformed_asm); 294690075Sobrien win: 294790075Sobrien bi->stack_out = regstack; 2948169689Skan bi->done = true; 294918334Speter} 295018334Speter 295190075Sobrien/* Convert registers in all blocks reachable from BLOCK. */ 295290075Sobrien 2953169689Skanstatic void 2954169689Skanconvert_regs_2 (basic_block block) 295518334Speter{ 295690075Sobrien basic_block *stack, *sp; 295718334Speter 2958122180Skan /* We process the blocks in a top-down manner, in a way such that one block 2959122180Skan is only processed after all its predecessors. The number of predecessors 2960122180Skan of every block has already been computed. */ 2961122180Skan 2962169689Skan stack = XNEWVEC (basic_block, n_basic_blocks); 296390075Sobrien sp = stack; 296490075Sobrien 296590075Sobrien *sp++ = block; 296690075Sobrien 296790075Sobrien do 296818334Speter { 296990075Sobrien edge e; 2970169689Skan edge_iterator ei; 297118334Speter 297290075Sobrien block = *--sp; 297318334Speter 2974122180Skan /* Processing BLOCK is achieved by convert_regs_1, which may purge 2975122180Skan some dead EH outgoing edge after the deletion of the trapping 2976122180Skan insn inside the block. Since the number of predecessors of 2977122180Skan BLOCK's successors was computed based on the initial edge set, 2978122180Skan we check the necessity to process some of these successors 2979122180Skan before such an edge deletion may happen. However, there is 2980122180Skan a pitfall: if BLOCK is the only predecessor of a successor and 2981122180Skan the edge between them happens to be deleted, the successor 2982122180Skan becomes unreachable and should not be processed. The problem 2983122180Skan is that there is no way to preventively detect this case so we 2984122180Skan stack the successor in all cases and hand over the task of 2985122180Skan fixing up the discrepancy to convert_regs_1. */ 2986122180Skan 2987169689Skan FOR_EACH_EDGE (e, ei, block->succs) 298890075Sobrien if (! (e->flags & EDGE_DFS_BACK)) 298990075Sobrien { 299090075Sobrien BLOCK_INFO (e->dest)->predecessors--; 299190075Sobrien if (!BLOCK_INFO (e->dest)->predecessors) 2992169689Skan *sp++ = e->dest; 299390075Sobrien } 2994122180Skan 2995169689Skan convert_regs_1 (block); 299618334Speter } 299790075Sobrien while (sp != stack); 299818334Speter 2999169689Skan free (stack); 300018334Speter} 300150397Sobrien 300290075Sobrien/* Traverse all basic blocks in a function, converting the register 300390075Sobrien references in each insn from the "flat" register file that gcc uses, 300490075Sobrien to the stack-like registers the 387 uses. */ 300590075Sobrien 3006169689Skanstatic void 3007169689Skanconvert_regs (void) 300818334Speter{ 3009117395Skan int inserted; 3010117395Skan basic_block b; 301190075Sobrien edge e; 3012169689Skan edge_iterator ei; 301318334Speter 301490075Sobrien /* Initialize uninitialized registers on function entry. */ 301590075Sobrien inserted = convert_regs_entry (); 301618334Speter 301790075Sobrien /* Construct the desired stack for function exit. */ 301890075Sobrien convert_regs_exit (); 301990075Sobrien BLOCK_INFO (EXIT_BLOCK_PTR)->done = 1; 302018334Speter 302190075Sobrien /* ??? Future: process inner loops first, and give them arbitrary 302290075Sobrien initial stacks which emit_swap_insn can modify. This ought to 3023169689Skan prevent double fxch that often appears at the head of a loop. */ 302418334Speter 302590075Sobrien /* Process all blocks reachable from all entry points. */ 3026169689Skan FOR_EACH_EDGE (e, ei, ENTRY_BLOCK_PTR->succs) 3027169689Skan convert_regs_2 (e->dest); 3028117395Skan 3029117395Skan /* ??? Process all unreachable blocks. Though there's no excuse 303090075Sobrien for keeping these even when not optimizing. */ 3031117395Skan FOR_EACH_BB (b) 303290075Sobrien { 303390075Sobrien block_info bi = BLOCK_INFO (b); 303418334Speter 303590075Sobrien if (! bi->done) 3036169689Skan convert_regs_2 (b); 303790075Sobrien } 3038169689Skan 3039169689Skan inserted |= compensate_edges (); 3040169689Skan 3041117395Skan clear_aux_for_blocks (); 304218334Speter 304396263Sobrien fixup_abnormal_edges (); 304490075Sobrien if (inserted) 304590075Sobrien commit_edge_insertions (); 304618334Speter 3047169689Skan if (dump_file) 3048169689Skan fputc ('\n', dump_file); 3049169689Skan} 3050169689Skan 3051169689Skan/* Convert register usage from "flat" register file usage to a "stack 3052169689Skan register file. FILE is the dump file, if used. 305318334Speter 3054169689Skan Construct a CFG and run life analysis. Then convert each insn one 3055169689Skan by one. Run a last cleanup_cfg pass, if optimizing, to eliminate 3056169689Skan code duplication created when the converter inserts pop insns on 3057169689Skan the edges. */ 3058169689Skan 3059169689Skanstatic bool 3060169689Skanreg_to_stack (void) 3061169689Skan{ 3062169689Skan basic_block bb; 3063169689Skan int i; 3064169689Skan int max_uid; 3065169689Skan 3066169689Skan /* Clean up previous run. */ 3067169689Skan if (stack_regs_mentioned_data != NULL) 3068169689Skan VEC_free (char, heap, stack_regs_mentioned_data); 3069169689Skan 3070169689Skan /* See if there is something to do. Flow analysis is quite 3071169689Skan expensive so we might save some compilation time. */ 3072169689Skan for (i = FIRST_STACK_REG; i <= LAST_STACK_REG; i++) 3073169689Skan if (regs_ever_live[i]) 3074169689Skan break; 3075169689Skan if (i > LAST_STACK_REG) 3076169689Skan return false; 3077169689Skan 3078169689Skan /* Ok, floating point instructions exist. If not optimizing, 3079169689Skan build the CFG and run life analysis. 3080169689Skan Also need to rebuild life when superblock scheduling is done 3081169689Skan as it don't update liveness yet. */ 3082169689Skan if (!optimize 3083169689Skan || ((flag_sched2_use_superblocks || flag_sched2_use_traces) 3084169689Skan && flag_schedule_insns_after_reload)) 3085169689Skan { 3086169689Skan count_or_remove_death_notes (NULL, 1); 3087169689Skan life_analysis (PROP_DEATH_NOTES); 3088169689Skan } 3089169689Skan mark_dfs_back_edges (); 3090169689Skan 3091169689Skan /* Set up block info for each basic block. */ 3092169689Skan alloc_aux_for_blocks (sizeof (struct block_info_def)); 3093169689Skan FOR_EACH_BB (bb) 3094169689Skan { 3095169689Skan block_info bi = BLOCK_INFO (bb); 3096169689Skan edge_iterator ei; 3097169689Skan edge e; 3098169689Skan int reg; 3099169689Skan 3100169689Skan FOR_EACH_EDGE (e, ei, bb->preds) 3101169689Skan if (!(e->flags & EDGE_DFS_BACK) 3102169689Skan && e->src != ENTRY_BLOCK_PTR) 3103169689Skan bi->predecessors++; 3104169689Skan 3105169689Skan /* Set current register status at last instruction `uninitialized'. */ 3106169689Skan bi->stack_in.top = -2; 3107169689Skan 3108169689Skan /* Copy live_at_end and live_at_start into temporaries. */ 3109169689Skan for (reg = FIRST_STACK_REG; reg <= LAST_STACK_REG; reg++) 3110169689Skan { 3111169689Skan if (REGNO_REG_SET_P (bb->il.rtl->global_live_at_end, reg)) 3112169689Skan SET_HARD_REG_BIT (bi->out_reg_set, reg); 3113169689Skan if (REGNO_REG_SET_P (bb->il.rtl->global_live_at_start, reg)) 3114169689Skan SET_HARD_REG_BIT (bi->stack_in.reg_set, reg); 3115169689Skan } 3116169689Skan } 3117169689Skan 3118169689Skan /* Create the replacement registers up front. */ 3119169689Skan for (i = FIRST_STACK_REG; i <= LAST_STACK_REG; i++) 3120169689Skan { 3121169689Skan enum machine_mode mode; 3122169689Skan for (mode = GET_CLASS_NARROWEST_MODE (MODE_FLOAT); 3123169689Skan mode != VOIDmode; 3124169689Skan mode = GET_MODE_WIDER_MODE (mode)) 3125169689Skan FP_MODE_REG (i, mode) = gen_rtx_REG (mode, i); 3126169689Skan for (mode = GET_CLASS_NARROWEST_MODE (MODE_COMPLEX_FLOAT); 3127169689Skan mode != VOIDmode; 3128169689Skan mode = GET_MODE_WIDER_MODE (mode)) 3129169689Skan FP_MODE_REG (i, mode) = gen_rtx_REG (mode, i); 3130169689Skan } 3131169689Skan 3132169689Skan ix86_flags_rtx = gen_rtx_REG (CCmode, FLAGS_REG); 3133169689Skan 3134169689Skan /* A QNaN for initializing uninitialized variables. 3135169689Skan 3136169689Skan ??? We can't load from constant memory in PIC mode, because 3137169689Skan we're inserting these instructions before the prologue and 3138169689Skan the PIC register hasn't been set up. In that case, fall back 3139169689Skan on zero, which we can get from `ldz'. */ 3140169689Skan 3141169689Skan if (flag_pic) 3142169689Skan not_a_num = CONST0_RTX (SFmode); 3143169689Skan else 3144169689Skan { 3145169689Skan not_a_num = gen_lowpart (SFmode, GEN_INT (0x7fc00000)); 3146169689Skan not_a_num = force_const_mem (SFmode, not_a_num); 3147169689Skan } 3148169689Skan 3149169689Skan /* Allocate a cache for stack_regs_mentioned. */ 3150169689Skan max_uid = get_max_uid (); 3151169689Skan stack_regs_mentioned_data = VEC_alloc (char, heap, max_uid + 1); 3152169689Skan memset (VEC_address (char, stack_regs_mentioned_data), 3153169689Skan 0, sizeof (char) * max_uid + 1); 3154169689Skan 3155169689Skan convert_regs (); 3156169689Skan 3157169689Skan free_aux_for_blocks (); 3158169689Skan return true; 315918334Speter} 316018334Speter#endif /* STACK_REGS */ 3161169689Skan 3162169689Skanstatic bool 3163169689Skangate_handle_stack_regs (void) 3164169689Skan{ 3165169689Skan#ifdef STACK_REGS 3166169689Skan return 1; 3167169689Skan#else 3168169689Skan return 0; 3169169689Skan#endif 3170169689Skan} 3171117395Skan 3172169689Skan/* Convert register usage from flat register file usage to a stack 3173169689Skan register file. */ 3174169689Skanstatic unsigned int 3175169689Skanrest_of_handle_stack_regs (void) 3176169689Skan{ 3177169689Skan#ifdef STACK_REGS 3178169689Skan if (reg_to_stack () && optimize) 3179169689Skan { 3180169689Skan regstack_completed = 1; 3181169689Skan if (cleanup_cfg (CLEANUP_EXPENSIVE | CLEANUP_POST_REGSTACK 3182169689Skan | (flag_crossjumping ? CLEANUP_CROSSJUMP : 0)) 3183169689Skan && (flag_reorder_blocks || flag_reorder_blocks_and_partition)) 3184169689Skan { 3185169689Skan reorder_basic_blocks (0); 3186169689Skan cleanup_cfg (CLEANUP_EXPENSIVE | CLEANUP_POST_REGSTACK); 3187169689Skan } 3188169689Skan } 3189169689Skan else 3190169689Skan regstack_completed = 1; 3191169689Skan#endif 3192169689Skan return 0; 3193169689Skan} 3194169689Skan 3195169689Skanstruct tree_opt_pass pass_stack_regs = 3196169689Skan{ 3197169689Skan "stack", /* name */ 3198169689Skan gate_handle_stack_regs, /* gate */ 3199169689Skan rest_of_handle_stack_regs, /* execute */ 3200169689Skan NULL, /* sub */ 3201169689Skan NULL, /* next */ 3202169689Skan 0, /* static_pass_number */ 3203169689Skan TV_REG_STACK, /* tv_id */ 3204169689Skan 0, /* properties_required */ 3205169689Skan 0, /* properties_provided */ 3206169689Skan 0, /* properties_destroyed */ 3207169689Skan 0, /* todo_flags_start */ 3208169689Skan TODO_dump_func | 3209169689Skan TODO_ggc_collect, /* todo_flags_finish */ 3210169689Skan 'k' /* letter */ 3211169689Skan}; 3212