⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 ia64.c

📁 gcc3.2.1源代码
💻 C
📖 第 1 页 / 共 5 页
字号:
/* Definitions of target machine for GNU compiler.   Copyright (C) 1999, 2000, 2001, 2002 Free Software Foundation, Inc.   Contributed by James E. Wilson <wilson@cygnus.com> and   		  David Mosberger <davidm@hpl.hp.com>.This file is part of GNU CC.GNU CC is free software; you can redistribute it and/or modifyit under the terms of the GNU General Public License as published bythe Free Software Foundation; either version 2, or (at your option)any later version.GNU CC is distributed in the hope that it will be useful,but WITHOUT ANY WARRANTY; without even the implied warranty ofMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See theGNU General Public License for more details.You should have received a copy of the GNU General Public Licensealong with GNU CC; see the file COPYING.  If not, write tothe Free Software Foundation, 59 Temple Place - Suite 330,Boston, MA 02111-1307, USA.  */#include "config.h"#include "system.h"#include "rtl.h"#include "tree.h"#include "regs.h"#include "hard-reg-set.h"#include "real.h"#include "insn-config.h"#include "conditions.h"#include "output.h"#include "insn-attr.h"#include "flags.h"#include "recog.h"#include "expr.h"#include "optabs.h"#include "obstack.h"#include "except.h"#include "function.h"#include "ggc.h"#include "basic-block.h"#include "toplev.h"#include "sched-int.h"#include "timevar.h"#include "target.h"#include "target-def.h"#include "tm_p.h"/* This is used for communication between ASM_OUTPUT_LABEL and   ASM_OUTPUT_LABELREF.  */int ia64_asm_output_label = 0;/* Define the information needed to generate branch and scc insns.  This is   stored from the compare operation.  */struct rtx_def * ia64_compare_op0;struct rtx_def * ia64_compare_op1;/* Register names for ia64_expand_prologue.  */static const char * const ia64_reg_numbers[96] ={ "r32", "r33", "r34", "r35", "r36", "r37", "r38", "r39",  "r40", "r41", "r42", "r43", "r44", "r45", "r46", "r47",  "r48", "r49", "r50", "r51", "r52", "r53", "r54", "r55",  "r56", "r57", "r58", "r59", "r60", "r61", "r62", "r63",  "r64", "r65", "r66", "r67", "r68", "r69", "r70", "r71",  "r72", "r73", "r74", "r75", "r76", "r77", "r78", "r79",  "r80", "r81", "r82", "r83", "r84", "r85", "r86", "r87",  "r88", "r89", "r90", "r91", "r92", "r93", "r94", "r95",  "r96", "r97", "r98", "r99", "r100","r101","r102","r103",  "r104","r105","r106","r107","r108","r109","r110","r111",  "r112","r113","r114","r115","r116","r117","r118","r119",  "r120","r121","r122","r123","r124","r125","r126","r127"};/* ??? These strings could be shared with REGISTER_NAMES.  */static const char * const ia64_input_reg_names[8] ={ "in0",  "in1",  "in2",  "in3",  "in4",  "in5",  "in6",  "in7" };/* ??? These strings could be shared with REGISTER_NAMES.  */static const char * const ia64_local_reg_names[80] ={ "loc0", "loc1", "loc2", "loc3", "loc4", "loc5", "loc6", "loc7",  "loc8", "loc9", "loc10","loc11","loc12","loc13","loc14","loc15",  "loc16","loc17","loc18","loc19","loc20","loc21","loc22","loc23",  "loc24","loc25","loc26","loc27","loc28","loc29","loc30","loc31",  "loc32","loc33","loc34","loc35","loc36","loc37","loc38","loc39",  "loc40","loc41","loc42","loc43","loc44","loc45","loc46","loc47",  "loc48","loc49","loc50","loc51","loc52","loc53","loc54","loc55",  "loc56","loc57","loc58","loc59","loc60","loc61","loc62","loc63",  "loc64","loc65","loc66","loc67","loc68","loc69","loc70","loc71",  "loc72","loc73","loc74","loc75","loc76","loc77","loc78","loc79" };/* ??? These strings could be shared with REGISTER_NAMES.  */static const char * const ia64_output_reg_names[8] ={ "out0", "out1", "out2", "out3", "out4", "out5", "out6", "out7" };/* String used with the -mfixed-range= option.  */const char *ia64_fixed_range_string;/* Determines whether we run our final scheduling pass or not.  We always   avoid the normal second scheduling pass.  */static int ia64_flag_schedule_insns2;/* Variables which are this size or smaller are put in the sdata/sbss   sections.  */unsigned int ia64_section_threshold;static int find_gr_spill PARAMS ((int));static int next_scratch_gr_reg PARAMS ((void));static void mark_reg_gr_used_mask PARAMS ((rtx, void *));static void ia64_compute_frame_size PARAMS ((HOST_WIDE_INT));static void setup_spill_pointers PARAMS ((int, rtx, HOST_WIDE_INT));static void finish_spill_pointers PARAMS ((void));static rtx spill_restore_mem PARAMS ((rtx, HOST_WIDE_INT));static void do_spill PARAMS ((rtx (*)(rtx, rtx, rtx), rtx, HOST_WIDE_INT, rtx));static void do_restore PARAMS ((rtx (*)(rtx, rtx, rtx), rtx, HOST_WIDE_INT));static rtx gen_movdi_x PARAMS ((rtx, rtx, rtx));static rtx gen_fr_spill_x PARAMS ((rtx, rtx, rtx));static rtx gen_fr_restore_x PARAMS ((rtx, rtx, rtx));static enum machine_mode hfa_element_mode PARAMS ((tree, int));static void fix_range PARAMS ((const char *));static void ia64_add_gc_roots PARAMS ((void));static void ia64_init_machine_status PARAMS ((struct function *));static void ia64_mark_machine_status PARAMS ((struct function *));static void ia64_free_machine_status PARAMS ((struct function *));static void emit_insn_group_barriers PARAMS ((FILE *, rtx));static void emit_all_insn_group_barriers PARAMS ((FILE *, rtx));static void emit_predicate_relation_info PARAMS ((void));static void process_epilogue PARAMS ((void));static int process_set PARAMS ((FILE *, rtx));static rtx ia64_expand_fetch_and_op PARAMS ((optab, enum machine_mode,					     tree, rtx));static rtx ia64_expand_op_and_fetch PARAMS ((optab, enum machine_mode,					     tree, rtx));static rtx ia64_expand_compare_and_swap PARAMS ((enum machine_mode, int,						 tree, rtx));static rtx ia64_expand_lock_test_and_set PARAMS ((enum machine_mode,						  tree, rtx));static rtx ia64_expand_lock_release PARAMS ((enum machine_mode, tree, rtx));static bool ia64_assemble_integer PARAMS ((rtx, unsigned int, int));static void ia64_output_function_prologue PARAMS ((FILE *, HOST_WIDE_INT));static void ia64_output_function_epilogue PARAMS ((FILE *, HOST_WIDE_INT));static void ia64_output_function_end_prologue PARAMS ((FILE *));static int ia64_issue_rate PARAMS ((void));static int ia64_adjust_cost PARAMS ((rtx, rtx, rtx, int));static void ia64_sched_init PARAMS ((FILE *, int, int));static void ia64_sched_finish PARAMS ((FILE *, int));static int ia64_internal_sched_reorder PARAMS ((FILE *, int, rtx *,						int *, int, int));static int ia64_sched_reorder PARAMS ((FILE *, int, rtx *, int *, int));static int ia64_sched_reorder2 PARAMS ((FILE *, int, rtx *, int *, int));static int ia64_variable_issue PARAMS ((FILE *, int, rtx, int));static rtx ia64_cycle_display PARAMS ((int, rtx));/* Table of valid machine attributes.  */static const struct attribute_spec ia64_attribute_table[] ={  /* { name, min_len, max_len, decl_req, type_req, fn_type_req, handler } */  { "syscall_linkage", 0, 0, false, true,  true,  NULL },  { NULL,              0, 0, false, false, false, NULL }};/* Initialize the GCC target structure.  */#undef TARGET_ATTRIBUTE_TABLE#define TARGET_ATTRIBUTE_TABLE ia64_attribute_table#undef TARGET_INIT_BUILTINS#define TARGET_INIT_BUILTINS ia64_init_builtins#undef TARGET_EXPAND_BUILTIN#define TARGET_EXPAND_BUILTIN ia64_expand_builtin#undef TARGET_ASM_BYTE_OP#define TARGET_ASM_BYTE_OP "\tdata1\t"#undef TARGET_ASM_ALIGNED_HI_OP#define TARGET_ASM_ALIGNED_HI_OP "\tdata2\t"#undef TARGET_ASM_ALIGNED_SI_OP#define TARGET_ASM_ALIGNED_SI_OP "\tdata4\t"#undef TARGET_ASM_ALIGNED_DI_OP#define TARGET_ASM_ALIGNED_DI_OP "\tdata8\t"#undef TARGET_ASM_UNALIGNED_HI_OP#define TARGET_ASM_UNALIGNED_HI_OP "\tdata2.ua\t"#undef TARGET_ASM_UNALIGNED_SI_OP#define TARGET_ASM_UNALIGNED_SI_OP "\tdata4.ua\t"#undef TARGET_ASM_UNALIGNED_DI_OP#define TARGET_ASM_UNALIGNED_DI_OP "\tdata8.ua\t"#undef TARGET_ASM_INTEGER#define TARGET_ASM_INTEGER ia64_assemble_integer#undef TARGET_ASM_FUNCTION_PROLOGUE#define TARGET_ASM_FUNCTION_PROLOGUE ia64_output_function_prologue#undef TARGET_ASM_FUNCTION_END_PROLOGUE#define TARGET_ASM_FUNCTION_END_PROLOGUE ia64_output_function_end_prologue#undef TARGET_ASM_FUNCTION_EPILOGUE#define TARGET_ASM_FUNCTION_EPILOGUE ia64_output_function_epilogue#undef TARGET_SCHED_ADJUST_COST#define TARGET_SCHED_ADJUST_COST ia64_adjust_cost#undef TARGET_SCHED_ISSUE_RATE#define TARGET_SCHED_ISSUE_RATE ia64_issue_rate#undef TARGET_SCHED_VARIABLE_ISSUE#define TARGET_SCHED_VARIABLE_ISSUE ia64_variable_issue#undef TARGET_SCHED_INIT#define TARGET_SCHED_INIT ia64_sched_init#undef TARGET_SCHED_FINISH#define TARGET_SCHED_FINISH ia64_sched_finish#undef TARGET_SCHED_REORDER#define TARGET_SCHED_REORDER ia64_sched_reorder#undef TARGET_SCHED_REORDER2#define TARGET_SCHED_REORDER2 ia64_sched_reorder2#undef TARGET_SCHED_CYCLE_DISPLAY#define TARGET_SCHED_CYCLE_DISPLAY ia64_cycle_displaystruct gcc_target targetm = TARGET_INITIALIZER;/* Return 1 if OP is a valid operand for the MEM of a CALL insn.  */intcall_operand (op, mode)     rtx op;     enum machine_mode mode;{  if (mode != GET_MODE (op))    return 0;  return (GET_CODE (op) == SYMBOL_REF || GET_CODE (op) == REG	  || (GET_CODE (op) == SUBREG && GET_CODE (XEXP (op, 0)) == REG));}/* Return 1 if OP refers to a symbol in the sdata section.  */intsdata_symbolic_operand (op, mode)     rtx op;     enum machine_mode mode ATTRIBUTE_UNUSED;{  switch (GET_CODE (op))    {    case CONST:      if (GET_CODE (XEXP (op, 0)) != PLUS	  || GET_CODE (XEXP (XEXP (op, 0), 0)) != SYMBOL_REF)	break;      op = XEXP (XEXP (op, 0), 0);      /* FALLTHRU */    case SYMBOL_REF:      if (CONSTANT_POOL_ADDRESS_P (op))	return GET_MODE_SIZE (get_pool_mode (op)) <= ia64_section_threshold;      else        return XSTR (op, 0)[0] == SDATA_NAME_FLAG_CHAR;    default:      break;    }  return 0;}/* Return 1 if OP refers to a symbol, and is appropriate for a GOT load.  */intgot_symbolic_operand (op, mode)     rtx op;     enum machine_mode mode ATTRIBUTE_UNUSED;{  switch (GET_CODE (op))    {    case CONST:      op = XEXP (op, 0);      if (GET_CODE (op) != PLUS)	return 0;      if (GET_CODE (XEXP (op, 0)) != SYMBOL_REF)	return 0;      op = XEXP (op, 1);      if (GET_CODE (op) != CONST_INT)	return 0;	return 1;      /* Ok if we're not using GOT entries at all.  */      if (TARGET_NO_PIC || TARGET_AUTO_PIC)	return 1;      /* "Ok" while emitting rtl, since otherwise we won't be provided	 with the entire offset during emission, which makes it very	 hard to split the offset into high and low parts.  */      if (rtx_equal_function_value_matters)	return 1;      /* Force the low 14 bits of the constant to zero so that we do not	 use up so many GOT entries.  */      return (INTVAL (op) & 0x3fff) == 0;    case SYMBOL_REF:    case LABEL_REF:      return 1;    default:      break;    }  return 0;}/* Return 1 if OP refers to a symbol.  */intsymbolic_operand (op, mode)     rtx op;     enum machine_mode mode ATTRIBUTE_UNUSED;{  switch (GET_CODE (op))    {    case CONST:    case SYMBOL_REF:    case LABEL_REF:      return 1;    default:      break;    }  return 0;}/* Return 1 if OP refers to a function.  */intfunction_operand (op, mode)     rtx op;     enum machine_mode mode ATTRIBUTE_UNUSED;{  if (GET_CODE (op) == SYMBOL_REF && SYMBOL_REF_FLAG (op))    return 1;  else    return 0;}/* Return 1 if OP is setjmp or a similar function.  *//* ??? This is an unsatisfying solution.  Should rethink.  */intsetjmp_operand (op, mode)     rtx op;     enum machine_mode mode ATTRIBUTE_UNUSED;{  const char *name;  int retval = 0;  if (GET_CODE (op) != SYMBOL_REF)    return 0;  name = XSTR (op, 0);  /* The following code is borrowed from special_function_p in calls.c.  */  /* Disregard prefix _, __ or __x.  */  if (name[0] == '_')    {      if (name[1] == '_' && name[2] == 'x')	name += 3;      else if (name[1] == '_')	name += 2;      else	name += 1;    }  if (name[0] == 's')    {      retval	= ((name[1] == 'e'	    && (! strcmp (name, "setjmp")		|| ! strcmp (name, "setjmp_syscall")))	   || (name[1] == 'i'	       && ! strcmp (name, "sigsetjmp"))	   || (name[1] == 'a'	       && ! strcmp (name, "savectx")));    }  else if ((name[0] == 'q' && name[1] == 's'	    && ! strcmp (name, "qsetjmp"))	   || (name[0] == 'v' && name[1] == 'f'	       && ! strcmp (name, "vfork")))    retval = 1;  return retval;}/* Return 1 if OP is a general operand, but when pic exclude symbolic   operands.  *//* ??? If we drop no-pic support, can delete SYMBOL_REF, CONST, and LABEL_REF   from PREDICATE_CODES.  */intmove_operand (op, mode)     rtx op;     enum machine_mode mode;{  if (! TARGET_NO_PIC && symbolic_operand (op, mode))    return 0;  return general_operand (op, mode);}/* Return 1 if OP is a register operand that is (or could be) a GR reg.  */intgr_register_operand (op, mode)     rtx op;     enum machine_mode mode;{  if (! register_operand (op, mode))    return 0;  if (GET_CODE (op) == SUBREG)    op = SUBREG_REG (op);  if (GET_CODE (op) == REG)    {      unsigned int regno = REGNO (op);      if (regno < FIRST_PSEUDO_REGISTER)	return GENERAL_REGNO_P (regno);    }  return 1;}/* Return 1 if OP is a register operand that is (or could be) an FR reg.  */intfr_register_operand (op, mode)     rtx op;     enum machine_mode mode;{  if (! register_operand (op, mode))    return 0;  if (GET_CODE (op) == SUBREG)    op = SUBREG_REG (op);  if (GET_CODE (op) == REG)    {      unsigned int regno = REGNO (op);      if (regno < FIRST_PSEUDO_REGISTER)	return FR_REGNO_P (regno);    }  return 1;}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -