i386.c

来自「gcc3.2.1源代码」· C语言 代码 · 共 1,901 行 · 第 1/5 页

C
1,901
字号
/* Subroutines used for code generation on IA-32.   Copyright (C) 1988, 1992, 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001,   2002 Free Software Foundation, Inc.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 "tm_p.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 "except.h"#include "function.h"#include "recog.h"#include "expr.h"#include "optabs.h"#include "toplev.h"#include "basic-block.h"#include "ggc.h"#include "target.h"#include "target-def.h"#ifndef CHECK_STACK_LIMIT#define CHECK_STACK_LIMIT (-1)#endif/* Processor costs (relative to an add) */static const struct processor_costs size_cost = {	/* costs for tunning for size */  2,					/* cost of an add instruction */  3,					/* cost of a lea instruction */  2,					/* variable shift costs */  3,					/* constant shift costs */  3,					/* cost of starting a multiply */  0,					/* cost of multiply per each bit set */  3,					/* cost of a divide/mod */  3,					/* cost of movsx */  3,					/* cost of movzx */  0,					/* "large" insn */  2,					/* MOVE_RATIO */  2,					/* cost for loading QImode using movzbl */  {2, 2, 2},				/* cost of loading integer registers					   in QImode, HImode and SImode.					   Relative to reg-reg move (2).  */  {2, 2, 2},				/* cost of storing integer registers */  2,					/* cost of reg,reg fld/fst */  {2, 2, 2},				/* cost of loading fp registers					   in SFmode, DFmode and XFmode */  {2, 2, 2},				/* cost of loading integer registers */  3,					/* cost of moving MMX register */  {3, 3},				/* cost of loading MMX registers					   in SImode and DImode */  {3, 3},				/* cost of storing MMX registers					   in SImode and DImode */  3,					/* cost of moving SSE register */  {3, 3, 3},				/* cost of loading SSE registers					   in SImode, DImode and TImode */  {3, 3, 3},				/* cost of storing SSE registers					   in SImode, DImode and TImode */  3,					/* MMX or SSE register to integer */  0,					/* size of prefetch block */  0,					/* number of parallel prefetches */};/* Processor costs (relative to an add) */static const struct processor_costs i386_cost = {	/* 386 specific costs */  1,					/* cost of an add instruction */  1,					/* cost of a lea instruction */  3,					/* variable shift costs */  2,					/* constant shift costs */  6,					/* cost of starting a multiply */  1,					/* cost of multiply per each bit set */  23,					/* cost of a divide/mod */  3,					/* cost of movsx */  2,					/* cost of movzx */  15,					/* "large" insn */  3,					/* MOVE_RATIO */  4,					/* cost for loading QImode using movzbl */  {2, 4, 2},				/* cost of loading integer registers					   in QImode, HImode and SImode.					   Relative to reg-reg move (2).  */  {2, 4, 2},				/* cost of storing integer registers */  2,					/* cost of reg,reg fld/fst */  {8, 8, 8},				/* cost of loading fp registers					   in SFmode, DFmode and XFmode */  {8, 8, 8},				/* cost of loading integer registers */  2,					/* cost of moving MMX register */  {4, 8},				/* cost of loading MMX registers					   in SImode and DImode */  {4, 8},				/* cost of storing MMX registers					   in SImode and DImode */  2,					/* cost of moving SSE register */  {4, 8, 16},				/* cost of loading SSE registers					   in SImode, DImode and TImode */  {4, 8, 16},				/* cost of storing SSE registers					   in SImode, DImode and TImode */  3,					/* MMX or SSE register to integer */  0,					/* size of prefetch block */  0,					/* number of parallel prefetches */};static const struct processor_costs i486_cost = {	/* 486 specific costs */  1,					/* cost of an add instruction */  1,					/* cost of a lea instruction */  3,					/* variable shift costs */  2,					/* constant shift costs */  12,					/* cost of starting a multiply */  1,					/* cost of multiply per each bit set */  40,					/* cost of a divide/mod */  3,					/* cost of movsx */  2,					/* cost of movzx */  15,					/* "large" insn */  3,					/* MOVE_RATIO */  4,					/* cost for loading QImode using movzbl */  {2, 4, 2},				/* cost of loading integer registers					   in QImode, HImode and SImode.					   Relative to reg-reg move (2).  */  {2, 4, 2},				/* cost of storing integer registers */  2,					/* cost of reg,reg fld/fst */  {8, 8, 8},				/* cost of loading fp registers					   in SFmode, DFmode and XFmode */  {8, 8, 8},				/* cost of loading integer registers */  2,					/* cost of moving MMX register */  {4, 8},				/* cost of loading MMX registers					   in SImode and DImode */  {4, 8},				/* cost of storing MMX registers					   in SImode and DImode */  2,					/* cost of moving SSE register */  {4, 8, 16},				/* cost of loading SSE registers					   in SImode, DImode and TImode */  {4, 8, 16},				/* cost of storing SSE registers					   in SImode, DImode and TImode */  3,					/* MMX or SSE register to integer */  0,					/* size of prefetch block */  0,					/* number of parallel prefetches */};static const struct processor_costs pentium_cost = {  1,					/* cost of an add instruction */  1,					/* cost of a lea instruction */  4,					/* variable shift costs */  1,					/* constant shift costs */  11,					/* cost of starting a multiply */  0,					/* cost of multiply per each bit set */  25,					/* cost of a divide/mod */  3,					/* cost of movsx */  2,					/* cost of movzx */  8,					/* "large" insn */  6,					/* MOVE_RATIO */  6,					/* cost for loading QImode using movzbl */  {2, 4, 2},				/* cost of loading integer registers					   in QImode, HImode and SImode.					   Relative to reg-reg move (2).  */  {2, 4, 2},				/* cost of storing integer registers */  2,					/* cost of reg,reg fld/fst */  {2, 2, 6},				/* cost of loading fp registers					   in SFmode, DFmode and XFmode */  {4, 4, 6},				/* cost of loading integer registers */  8,					/* cost of moving MMX register */  {8, 8},				/* cost of loading MMX registers					   in SImode and DImode */  {8, 8},				/* cost of storing MMX registers					   in SImode and DImode */  2,					/* cost of moving SSE register */  {4, 8, 16},				/* cost of loading SSE registers					   in SImode, DImode and TImode */  {4, 8, 16},				/* cost of storing SSE registers					   in SImode, DImode and TImode */  3,					/* MMX or SSE register to integer */  0,					/* size of prefetch block */  0,					/* number of parallel prefetches */};static const struct processor_costs pentiumpro_cost = {  1,					/* cost of an add instruction */  1,					/* cost of a lea instruction */  1,					/* variable shift costs */  1,					/* constant shift costs */  4,					/* cost of starting a multiply */  0,					/* cost of multiply per each bit set */  17,					/* cost of a divide/mod */  1,					/* cost of movsx */  1,					/* cost of movzx */  8,					/* "large" insn */  6,					/* MOVE_RATIO */  2,					/* cost for loading QImode using movzbl */  {4, 4, 4},				/* cost of loading integer registers					   in QImode, HImode and SImode.					   Relative to reg-reg move (2).  */  {2, 2, 2},				/* cost of storing integer registers */  2,					/* cost of reg,reg fld/fst */  {2, 2, 6},				/* cost of loading fp registers					   in SFmode, DFmode and XFmode */  {4, 4, 6},				/* cost of loading integer registers */  2,					/* cost of moving MMX register */  {2, 2},				/* cost of loading MMX registers					   in SImode and DImode */  {2, 2},				/* cost of storing MMX registers					   in SImode and DImode */  2,					/* cost of moving SSE register */  {2, 2, 8},				/* cost of loading SSE registers					   in SImode, DImode and TImode */  {2, 2, 8},				/* cost of storing SSE registers					   in SImode, DImode and TImode */  3,					/* MMX or SSE register to integer */  32,					/* size of prefetch block */  6,					/* number of parallel prefetches */};static const struct processor_costs k6_cost = {  1,					/* cost of an add instruction */  2,					/* cost of a lea instruction */  1,					/* variable shift costs */  1,					/* constant shift costs */  3,					/* cost of starting a multiply */  0,					/* cost of multiply per each bit set */  18,					/* cost of a divide/mod */  2,					/* cost of movsx */  2,					/* cost of movzx */  8,					/* "large" insn */  4,					/* MOVE_RATIO */  3,					/* cost for loading QImode using movzbl */  {4, 5, 4},				/* cost of loading integer registers					   in QImode, HImode and SImode.					   Relative to reg-reg move (2).  */  {2, 3, 2},				/* cost of storing integer registers */  4,					/* cost of reg,reg fld/fst */  {6, 6, 6},				/* cost of loading fp registers					   in SFmode, DFmode and XFmode */  {4, 4, 4},				/* cost of loading integer registers */  2,					/* cost of moving MMX register */  {2, 2},				/* cost of loading MMX registers					   in SImode and DImode */  {2, 2},				/* cost of storing MMX registers					   in SImode and DImode */  2,					/* cost of moving SSE register */  {2, 2, 8},				/* cost of loading SSE registers					   in SImode, DImode and TImode */  {2, 2, 8},				/* cost of storing SSE registers					   in SImode, DImode and TImode */  6,					/* MMX or SSE register to integer */  32,					/* size of prefetch block */  1,					/* number of parallel prefetches */};static const struct processor_costs athlon_cost = {  1,					/* cost of an add instruction */  2,					/* cost of a lea instruction */  1,					/* variable shift costs */  1,					/* constant shift costs */  5,					/* cost of starting a multiply */  0,					/* cost of multiply per each bit set */  42,					/* cost of a divide/mod */  1,					/* cost of movsx */  1,					/* cost of movzx */  8,					/* "large" insn */  9,					/* MOVE_RATIO */  4,					/* cost for loading QImode using movzbl */  {3, 4, 3},				/* cost of loading integer registers					   in QImode, HImode and SImode.					   Relative to reg-reg move (2).  */  {3, 4, 3},				/* cost of storing integer registers */  4,					/* cost of reg,reg fld/fst */  {4, 4, 12},				/* cost of loading fp registers					   in SFmode, DFmode and XFmode */  {6, 6, 8},				/* cost of loading integer registers */  2,					/* cost of moving MMX register */  {4, 4},				/* cost of loading MMX registers					   in SImode and DImode */  {4, 4},				/* cost of storing MMX registers					   in SImode and DImode */  2,					/* cost of moving SSE register */  {4, 4, 6},				/* cost of loading SSE registers					   in SImode, DImode and TImode */  {4, 4, 5},				/* cost of storing SSE registers					   in SImode, DImode and TImode */  5,					/* MMX or SSE register to integer */  64,					/* size of prefetch block */  6,					/* number of parallel prefetches */};static const struct processor_costs pentium4_cost = {  1,					/* cost of an add instruction */  1,					/* cost of a lea instruction */  8,					/* variable shift costs */  8,					/* constant shift costs */  30,					/* cost of starting a multiply */  0,					/* cost of multiply per each bit set */  112,					/* cost of a divide/mod */  1,					/* cost of movsx */  1,					/* cost of movzx */  16,					/* "large" insn */  6,					/* MOVE_RATIO */  2,					/* cost for loading QImode using movzbl */  {4, 5, 4},				/* cost of loading integer registers					   in QImode, HImode and SImode.					   Relative to reg-reg move (2).  */  {2, 3, 2},				/* cost of storing integer registers */  2,					/* cost of reg,reg fld/fst */  {2, 2, 6},				/* cost of loading fp registers					   in SFmode, DFmode and XFmode */  {4, 4, 6},				/* cost of loading integer registers */  2,					/* cost of moving MMX register */  {2, 2},				/* cost of loading MMX registers					   in SImode and DImode */  {2, 2},				/* cost of storing MMX registers					   in SImode and DImode */  12,					/* cost of moving SSE register */  {12, 12, 12},				/* cost of loading SSE registers					   in SImode, DImode and TImode */  {2, 2, 8},				/* cost of storing SSE registers					   in SImode, DImode and TImode */  10,					/* MMX or SSE register to integer */  64,					/* size of prefetch block */  6,					/* number of parallel prefetches */};const struct processor_costs *ix86_cost = &pentium_cost;/* Processor feature/optimization bitmasks.  */#define m_386 (1<<PROCESSOR_I386)#define m_486 (1<<PROCESSOR_I486)#define m_PENT (1<<PROCESSOR_PENTIUM)#define m_PPRO (1<<PROCESSOR_PENTIUMPRO)#define m_K6  (1<<PROCESSOR_K6)#define m_ATHLON  (1<<PROCESSOR_ATHLON)#define m_PENT4  (1<<PROCESSOR_PENTIUM4)const int x86_use_leave = m_386 | m_K6 | m_ATHLON;const int x86_push_memory = m_386 | m_K6 | m_ATHLON | m_PENT4;const int x86_zero_extend_with_and = m_486 | m_PENT;const int x86_movx = m_ATHLON | m_PPRO | m_PENT4 /* m_386 | m_K6 */;const int x86_double_with_add = ~m_386;const int x86_use_bit_test = m_386;const int x86_unroll_strlen = m_486 | m_PENT | m_PPRO | m_ATHLON | m_K6;const int x86_cmove = m_PPRO | m_ATHLON | m_PENT4;const int x86_3dnow_a = m_ATHLON;const int x86_deep_branch = m_PPRO | m_K6 | m_ATHLON | m_PENT4;const int x86_branch_hints = m_PENT4;const int x86_use_sahf = m_PPRO | m_K6 | m_PENT4;const int x86_partial_reg_stall = m_PPRO;const int x86_use_loop = m_K6;const int x86_use_fiop = ~(m_PPRO | m_ATHLON | m_PENT);const int x86_use_mov0 = m_K6;const int x86_use_cltd = ~(m_PENT | m_K6);const int x86_read_modify_write = ~m_PENT;const int x86_read_modify = ~(m_PENT | m_PPRO);const int x86_split_long_moves = m_PPRO;const int x86_promote_QImode = m_K6 | m_PENT | m_386 | m_486;const int x86_single_stringop = m_386 | m_PENT4;const int x86_qimode_math = ~(0);const int x86_promote_qi_regs = 0;

⌨️ 快捷键说明

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