Skip to content
Projects
Groups
Snippets
Help
This project
Loading...
Sign in / Register
Toggle navigation
R
riscv-gcc-1
Overview
Overview
Details
Activity
Cycle Analytics
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Issues
0
Issues
0
List
Board
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Charts
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
lvzhengyang
riscv-gcc-1
Commits
91ce572a
Commit
91ce572a
authored
Oct 18, 2000
by
Chandrakala Chavva
Committed by
Chandra Chavva
Oct 18, 2000
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
Adding new option -ftrapv.
From-SVN: r36942
parent
4c2c5712
Expand all
Hide whitespace changes
Inline
Side-by-side
Showing
13 changed files
with
347 additions
and
37 deletions
+347
-37
gcc/ChangeLog
+44
-0
gcc/Makefile.in
+2
-0
gcc/expmed.c
+33
-13
gcc/expr.c
+28
-11
gcc/expr.h
+13
-1
gcc/flags.h
+4
-0
gcc/genopinit.c
+40
-9
gcc/invoke.texi
+5
-1
gcc/libgcc2.c
+170
-0
gcc/loop.c
+2
-2
gcc/optabs.c
+0
-0
gcc/toplev.c
+4
-0
gcc/tree.h
+2
-0
No files found.
gcc/ChangeLog
View file @
91ce572a
2000-10-18 Chandrakala Chavva <cchavva@redhat.com>
* expmed.c (expand_mult): Don't do synth_mult optimization for -ftrapv.
Use smulv_optab for -ftrapv.
(expand_mult_highpart): Use unsigned multiply.
(expand_divmod): Special-case division by -1.
For EXACT_DIV_EXPR, do right shift first, then the multiply.
For complex divide, use abs with unsigned result.
* expr.c (force_operand): Use unsigned multiply.
(expand_expr): Use overflow-trapping optabs for signed types if
flag_trapv.
If flag_trapv, don't generate a recursive call with EXPAND_SUM
if the type is signed and the original call wasn't EXPAND_SUM or
EXPAND_INITIALIZER.
* expr.h (addv_optab, subv_optab, smulv_optab, sdivv_optab): Declare.
(negv_optab, absv_optab): Declare.
* flags.h (flag_trapv): Declare.
* genopinit.c (optabs): Add entries for addv_optab, subv_optab,
smulv_optab, sdivv_optab, negv_optab and absv_optab.
(gen_insn): Interpret '$P' as requiring an integer mode,
including partial integer modes.
* loop.c (emit_iv_add_mult): Use unsigned expand_mult_add.
(product_cheap_p): Use unsigned expand_mult.
* optabs.c (addv_optab, subv_optab, smulv_optab, sdivv_optab): Define.
(negv_optab, absv_optab): Define.
(expand_binop): Use overflow-trapping optabs for signed types if
flag_trapv.
Handle negv_optab libe neg_optab.
(expand_abs): Take result_unsignedp argument instead of unsignedp one.
Use overflow-trapping optabs for signed result if flag_trapv.
(expand_complex_abs): Use overflow-trapping optabs for signed types if
flag_trapv.
Don't open-code complex absolute-value operation for flag_trapv.
(init_optabs): Initialize addv_optab, subv_optab, smulv_optab,
sdivv_optab, negv_optab and absv_optab.
* toplev.c (flag_trapv): Define.
(lang_independent_options f_options): Include flag_trapv.
* tree.h (TYPE_TRAP_SIGNED): Define.
* libgcc2.c (__addvsi3, __addvdi3, __subvsi3,__subvsi3, __subvdi3,
__mulvsi3, __negvsi2, __negvdi2, __absvsi2, __absvdi2, __mulvdi3):
New functions.
* Makefile.in: add _absvsi2 _absvdi2 _addvsi3 _addvdi3 _subvsi3
_subvdi3 _mulvsi3 _mulvdi3 _negvsi2 _negvdi2.
2000-10-18 Geoffrey Keating <geoffk@cygnus.com>
2000-10-18 Geoffrey Keating <geoffk@cygnus.com>
David V. Henkel-Wallace <gumby@cygnus.com>
David V. Henkel-Wallace <gumby@cygnus.com>
...
...
gcc/Makefile.in
View file @
91ce572a
...
@@ -754,6 +754,8 @@ LIB2FUNCS = _muldi3 _divdi3 _moddi3 _udivdi3 _umoddi3 _negdi2 \
...
@@ -754,6 +754,8 @@ LIB2FUNCS = _muldi3 _divdi3 _moddi3 _udivdi3 _umoddi3 _negdi2 \
_fixtfdi _fixunstfdi _floatditf
\
_fixtfdi _fixunstfdi _floatditf
\
__gcc_bcmp _varargs __dummy _eprintf
\
__gcc_bcmp _varargs __dummy _eprintf
\
_bb _shtab _clear_cache _trampoline __main _exit
\
_bb _shtab _clear_cache _trampoline __main _exit
\
_absvsi2 _absvdi2 _addvsi3 _addvdi3 _subvsi3 _subvdi3
\
_mulvsi3 _mulvdi3 _negvsi2 _negvdi2
\
_ctors
_ctors
LIB2FUNCS_EH
=
_eh
LIB2FUNCS_EH
=
_eh
...
...
gcc/expmed.c
View file @
91ce572a
...
@@ -2358,7 +2358,8 @@ expand_mult (mode, op0, op1, target, unsignedp)
...
@@ -2358,7 +2358,8 @@ expand_mult (mode, op0, op1, target, unsignedp)
But this causes such a terrible slowdown sometimes
But this causes such a terrible slowdown sometimes
that it seems better to use synth_mult always. */
that it seems better to use synth_mult always. */
if
(
const_op1
&&
GET_CODE
(
const_op1
)
==
CONST_INT
)
if
(
const_op1
&&
GET_CODE
(
const_op1
)
==
CONST_INT
&&
(
unsignedp
||
!
flag_trapv
))
{
{
struct
algorithm
alg
;
struct
algorithm
alg
;
struct
algorithm
alg2
;
struct
algorithm
alg2
;
...
@@ -2531,7 +2532,10 @@ expand_mult (mode, op0, op1, target, unsignedp)
...
@@ -2531,7 +2532,10 @@ expand_mult (mode, op0, op1, target, unsignedp)
/* This used to use umul_optab if unsigned, but for non-widening multiply
/* This used to use umul_optab if unsigned, but for non-widening multiply
there is no difference between signed and unsigned. */
there is no difference between signed and unsigned. */
op0
=
expand_binop
(
mode
,
smul_optab
,
op0
=
expand_binop
(
mode
,
!
unsignedp
&&
flag_trapv
&&
(
GET_MODE_CLASS
(
mode
)
==
MODE_INT
)
?
smulv_optab
:
smul_optab
,
op0
,
op1
,
target
,
unsignedp
,
OPTAB_LIB_WIDEN
);
op0
,
op1
,
target
,
unsignedp
,
OPTAB_LIB_WIDEN
);
if
(
op0
==
0
)
if
(
op0
==
0
)
abort
();
abort
();
...
@@ -2775,7 +2779,9 @@ expand_mult_highpart (mode, op0, cnst1, target, unsignedp, max_cost)
...
@@ -2775,7 +2779,9 @@ expand_mult_highpart (mode, op0, cnst1, target, unsignedp, max_cost)
multiply. Maybe change expand_binop to handle widening multiply? */
multiply. Maybe change expand_binop to handle widening multiply? */
op0
=
convert_to_mode
(
wider_mode
,
op0
,
unsignedp
);
op0
=
convert_to_mode
(
wider_mode
,
op0
,
unsignedp
);
tem
=
expand_mult
(
wider_mode
,
op0
,
wide_op1
,
NULL_RTX
,
unsignedp
);
/* We know that this can't have signed overflow, so pretend this is
an unsigned multiply. */
tem
=
expand_mult
(
wider_mode
,
op0
,
wide_op1
,
NULL_RTX
,
0
);
tem
=
expand_shift
(
RSHIFT_EXPR
,
wider_mode
,
tem
,
tem
=
expand_shift
(
RSHIFT_EXPR
,
wider_mode
,
tem
,
build_int_2
(
size
,
0
),
NULL_RTX
,
1
);
build_int_2
(
size
,
0
),
NULL_RTX
,
1
);
return
convert_modes
(
mode
,
wider_mode
,
tem
,
unsignedp
);
return
convert_modes
(
mode
,
wider_mode
,
tem
,
unsignedp
);
...
@@ -2968,6 +2974,16 @@ expand_divmod (rem_flag, code, mode, op0, op1, target, unsignedp)
...
@@ -2968,6 +2974,16 @@ expand_divmod (rem_flag, code, mode, op0, op1, target, unsignedp)
if
(
op1
==
const1_rtx
)
if
(
op1
==
const1_rtx
)
return
rem_flag
?
const0_rtx
:
op0
;
return
rem_flag
?
const0_rtx
:
op0
;
/* When dividing by -1, we could get an overflow.
negv_optab can handle overflows. */
if
(
!
unsignedp
&&
op1
==
constm1_rtx
)
{
if
(
rem_flag
)
return
const0_rtx
;
return
expand_unop
(
mode
,
flag_trapv
&&
GET_MODE_CLASS
(
mode
)
==
MODE_INT
?
negv_optab
:
neg_optab
,
op0
,
target
,
0
);
}
if
(
target
if
(
target
/* Don't use the function value register as a target
/* Don't use the function value register as a target
since we have to read it as well as write it,
since we have to read it as well as write it,
...
@@ -3764,16 +3780,15 @@ expand_divmod (rem_flag, code, mode, op0, op1, target, unsignedp)
...
@@ -3764,16 +3780,15 @@ expand_divmod (rem_flag, code, mode, op0, op1, target, unsignedp)
{
{
HOST_WIDE_INT
d
=
INTVAL
(
op1
);
HOST_WIDE_INT
d
=
INTVAL
(
op1
);
unsigned
HOST_WIDE_INT
ml
;
unsigned
HOST_WIDE_INT
ml
;
int
p
ost
_shift
;
int
p
re
_shift
;
rtx
t1
;
rtx
t1
;
post_shift
=
floor_log2
(
d
&
-
d
);
pre_shift
=
floor_log2
(
d
&
-
d
);
ml
=
invert_mod2n
(
d
>>
post_shift
,
size
);
ml
=
invert_mod2n
(
d
>>
pre_shift
,
size
);
t1
=
expand_mult
(
compute_mode
,
op0
,
GEN_INT
(
ml
),
NULL_RTX
,
t1
=
expand_shift
(
RSHIFT_EXPR
,
compute_mode
,
op0
,
unsignedp
);
build_int_2
(
pre_shift
,
0
),
NULL_RTX
,
unsignedp
);
quotient
=
expand_shift
(
RSHIFT_EXPR
,
compute_mode
,
t1
,
quotient
=
expand_mult
(
compute_mode
,
t1
,
GEN_INT
(
ml
),
NULL_RTX
,
build_int_2
(
post_shift
,
0
),
0
);
NULL_RTX
,
unsignedp
);
insn
=
get_last_insn
();
insn
=
get_last_insn
();
set_unique_reg_note
(
insn
,
set_unique_reg_note
(
insn
,
...
@@ -3826,8 +3841,8 @@ expand_divmod (rem_flag, code, mode, op0, op1, target, unsignedp)
...
@@ -3826,8 +3841,8 @@ expand_divmod (rem_flag, code, mode, op0, op1, target, unsignedp)
remainder
=
expand_binop
(
compute_mode
,
sub_optab
,
op0
,
tem
,
remainder
=
expand_binop
(
compute_mode
,
sub_optab
,
op0
,
tem
,
remainder
,
0
,
OPTAB_LIB_WIDEN
);
remainder
,
0
,
OPTAB_LIB_WIDEN
);
}
}
abs_rem
=
expand_abs
(
compute_mode
,
remainder
,
NULL_RTX
,
0
);
abs_rem
=
expand_abs
(
compute_mode
,
remainder
,
NULL_RTX
,
1
,
0
);
abs_op1
=
expand_abs
(
compute_mode
,
op1
,
NULL_RTX
,
0
);
abs_op1
=
expand_abs
(
compute_mode
,
op1
,
NULL_RTX
,
1
,
0
);
tem
=
expand_shift
(
LSHIFT_EXPR
,
compute_mode
,
abs_rem
,
tem
=
expand_shift
(
LSHIFT_EXPR
,
compute_mode
,
abs_rem
,
build_int_2
(
1
,
0
),
NULL_RTX
,
1
);
build_int_2
(
1
,
0
),
NULL_RTX
,
1
);
do_cmp_and_jump
(
tem
,
abs_op1
,
LTU
,
compute_mode
,
label
);
do_cmp_and_jump
(
tem
,
abs_op1
,
LTU
,
compute_mode
,
label
);
...
@@ -4477,6 +4492,11 @@ emit_store_flag (target, code, op0, op1, mode, unsignedp, normalizep)
...
@@ -4477,6 +4492,11 @@ emit_store_flag (target, code, op0, op1, mode, unsignedp, normalizep)
we can use zero-extension to the wider mode (an unsigned conversion)
we can use zero-extension to the wider mode (an unsigned conversion)
as the operation. */
as the operation. */
/* CYGNUS LOCAL - amylaar/-ftrapv: Note that ABS doesn't yield a
positive number for INT_MIN, but that is compensated by the
subsequent overflow when subtracting one / negating.
END CYGNUS LOCAL */
if
(
abs_optab
->
handlers
[(
int
)
mode
].
insn_code
!=
CODE_FOR_nothing
)
if
(
abs_optab
->
handlers
[(
int
)
mode
].
insn_code
!=
CODE_FOR_nothing
)
tem
=
expand_unop
(
mode
,
abs_optab
,
op0
,
subtarget
,
1
);
tem
=
expand_unop
(
mode
,
abs_optab
,
op0
,
subtarget
,
1
);
else
if
(
ffs_optab
->
handlers
[(
int
)
mode
].
insn_code
!=
CODE_FOR_nothing
)
else
if
(
ffs_optab
->
handlers
[(
int
)
mode
].
insn_code
!=
CODE_FOR_nothing
)
...
...
gcc/expr.c
View file @
91ce572a
...
@@ -5307,7 +5307,7 @@ force_operand (value, target)
...
@@ -5307,7 +5307,7 @@ force_operand (value, target)
tmp
=
force_operand
(
XEXP
(
value
,
0
),
subtarget
);
tmp
=
force_operand
(
XEXP
(
value
,
0
),
subtarget
);
return
expand_mult
(
GET_MODE
(
value
),
tmp
,
return
expand_mult
(
GET_MODE
(
value
),
tmp
,
force_operand
(
op2
,
NULL_RTX
),
force_operand
(
op2
,
NULL_RTX
),
target
,
0
);
target
,
1
);
}
}
if
(
binoptab
)
if
(
binoptab
)
...
@@ -7248,7 +7248,9 @@ expand_expr (exp, target, tmode, modifier)
...
@@ -7248,7 +7248,9 @@ expand_expr (exp, target, tmode, modifier)
/* We come here from MINUS_EXPR when the second operand is a
/* We come here from MINUS_EXPR when the second operand is a
constant. */
constant. */
plus_expr
:
plus_expr
:
this_optab
=
add_optab
;
this_optab
=
!
unsignedp
&&
flag_trapv
&&
(
GET_MODE_CLASS
(
mode
)
==
MODE_INT
)
?
addv_optab
:
add_optab
;
/* If we are adding a constant, an RTL_EXPR that is sp, fp, or ap, and
/* If we are adding a constant, an RTL_EXPR that is sp, fp, or ap, and
something else, make sure we add the register to the constant and
something else, make sure we add the register to the constant and
...
@@ -7283,7 +7285,7 @@ expand_expr (exp, target, tmode, modifier)
...
@@ -7283,7 +7285,7 @@ expand_expr (exp, target, tmode, modifier)
If this is an EXPAND_SUM call, always return the sum. */
If this is an EXPAND_SUM call, always return the sum. */
if
(
modifier
==
EXPAND_SUM
||
modifier
==
EXPAND_INITIALIZER
if
(
modifier
==
EXPAND_SUM
||
modifier
==
EXPAND_INITIALIZER
||
mode
==
ptr_mode
)
||
(
mode
==
ptr_mode
&&
(
unsignedp
||
!
flag_trapv
))
)
{
{
if
(
TREE_CODE
(
TREE_OPERAND
(
exp
,
0
))
==
INTEGER_CST
if
(
TREE_CODE
(
TREE_OPERAND
(
exp
,
0
))
==
INTEGER_CST
&&
GET_MODE_BITSIZE
(
mode
)
<=
HOST_BITS_PER_WIDE_INT
&&
GET_MODE_BITSIZE
(
mode
)
<=
HOST_BITS_PER_WIDE_INT
...
@@ -7441,7 +7443,9 @@ expand_expr (exp, target, tmode, modifier)
...
@@ -7441,7 +7443,9 @@ expand_expr (exp, target, tmode, modifier)
goto
plus_expr
;
goto
plus_expr
;
}
}
}
}
this_optab
=
sub_optab
;
this_optab
=
!
unsignedp
&&
flag_trapv
&&
(
GET_MODE_CLASS
(
mode
)
==
MODE_INT
)
?
subv_optab
:
sub_optab
;
goto
binop
;
goto
binop
;
case
MULT_EXPR
:
case
MULT_EXPR
:
...
@@ -7624,7 +7628,10 @@ expand_expr (exp, target, tmode, modifier)
...
@@ -7624,7 +7628,10 @@ expand_expr (exp, target, tmode, modifier)
case
NEGATE_EXPR
:
case
NEGATE_EXPR
:
op0
=
expand_expr
(
TREE_OPERAND
(
exp
,
0
),
subtarget
,
VOIDmode
,
0
);
op0
=
expand_expr
(
TREE_OPERAND
(
exp
,
0
),
subtarget
,
VOIDmode
,
0
);
temp
=
expand_unop
(
mode
,
neg_optab
,
op0
,
target
,
0
);
temp
=
expand_unop
(
mode
,
!
unsignedp
&&
flag_trapv
&&
(
GET_MODE_CLASS
(
mode
)
==
MODE_INT
)
?
negv_optab
:
neg_optab
,
op0
,
target
,
0
);
if
(
temp
==
0
)
if
(
temp
==
0
)
abort
();
abort
();
return
temp
;
return
temp
;
...
@@ -7642,7 +7649,7 @@ expand_expr (exp, target, tmode, modifier)
...
@@ -7642,7 +7649,7 @@ expand_expr (exp, target, tmode, modifier)
if
(
TREE_UNSIGNED
(
type
))
if
(
TREE_UNSIGNED
(
type
))
return
op0
;
return
op0
;
return
expand_abs
(
mode
,
op0
,
target
,
return
expand_abs
(
mode
,
op0
,
target
,
unsignedp
,
safe_from_p
(
target
,
TREE_OPERAND
(
exp
,
0
),
1
));
safe_from_p
(
target
,
TREE_OPERAND
(
exp
,
0
),
1
));
case
MAX_EXPR
:
case
MAX_EXPR
:
...
@@ -7964,10 +7971,14 @@ expand_expr (exp, target, tmode, modifier)
...
@@ -7964,10 +7971,14 @@ expand_expr (exp, target, tmode, modifier)
&&
TREE_CODE_CLASS
(
TREE_CODE
(
TREE_OPERAND
(
exp
,
0
)))
==
'<'
)
&&
TREE_CODE_CLASS
(
TREE_CODE
(
TREE_OPERAND
(
exp
,
0
)))
==
'<'
)
{
{
rtx
result
;
rtx
result
;
optab
boptab
=
(
TREE_CODE
(
binary_op
)
==
PLUS_EXPR
?
add_optab
optab
boptab
=
(
TREE_CODE
(
binary_op
)
==
PLUS_EXPR
:
TREE_CODE
(
binary_op
)
==
MINUS_EXPR
?
sub_optab
?
(
TYPE_TRAP_SIGNED
(
TREE_TYPE
(
binary_op
))
:
TREE_CODE
(
binary_op
)
==
BIT_IOR_EXPR
?
ior_optab
?
addv_optab
:
add_optab
)
:
xor_optab
);
:
TREE_CODE
(
binary_op
)
==
MINUS_EXPR
?
(
TYPE_TRAP_SIGNED
(
TREE_TYPE
(
binary_op
))
?
subv_optab
:
sub_optab
)
:
TREE_CODE
(
binary_op
)
==
BIT_IOR_EXPR
?
ior_optab
:
xor_optab
);
/* If we had X ? A : A + 1, do this as A + (X == 0).
/* If we had X ? A : A + 1, do this as A + (X == 0).
...
@@ -8491,7 +8502,10 @@ expand_expr (exp, target, tmode, modifier)
...
@@ -8491,7 +8502,10 @@ expand_expr (exp, target, tmode, modifier)
gen_realpart
(
partmode
,
op0
));
gen_realpart
(
partmode
,
op0
));
imag_t
=
gen_imagpart
(
partmode
,
target
);
imag_t
=
gen_imagpart
(
partmode
,
target
);
temp
=
expand_unop
(
partmode
,
neg_optab
,
temp
=
expand_unop
(
partmode
,
!
unsignedp
&&
flag_trapv
&&
(
GET_MODE_CLASS
(
partmode
)
==
MODE_INT
)
?
negv_optab
:
neg_optab
,
gen_imagpart
(
partmode
,
op0
),
imag_t
,
0
);
gen_imagpart
(
partmode
,
op0
),
imag_t
,
0
);
if
(
temp
!=
imag_t
)
if
(
temp
!=
imag_t
)
emit_move_insn
(
imag_t
,
temp
);
emit_move_insn
(
imag_t
,
temp
);
...
@@ -9045,6 +9059,9 @@ expand_increment (exp, post, ignore)
...
@@ -9045,6 +9059,9 @@ expand_increment (exp, post, ignore)
this_optab
=
add_optab
;
this_optab
=
add_optab
;
}
}
if
(
TYPE_TRAP_SIGNED
(
TREE_TYPE
(
exp
)))
this_optab
=
this_optab
==
add_optab
?
addv_optab
:
subv_optab
;
/* For a preincrement, see if we can do this with a single instruction. */
/* For a preincrement, see if we can do this with a single instruction. */
if
(
!
post
)
if
(
!
post
)
{
{
...
...
gcc/expr.h
View file @
91ce572a
...
@@ -298,10 +298,13 @@ typedef struct optab
...
@@ -298,10 +298,13 @@ typedef struct optab
enum
optab_index
enum
optab_index
{
{
OTI_add
,
OTI_add
,
OTI_addv
,
OTI_sub
,
OTI_sub
,
OTI_subv
,
/* Signed and fp multiply */
/* Signed and fp multiply */
OTI_smul
,
OTI_smul
,
OTI_smulv
,
/* Signed multiply, return high word */
/* Signed multiply, return high word */
OTI_smul_highpart
,
OTI_smul_highpart
,
OTI_umul_highpart
,
OTI_umul_highpart
,
...
@@ -311,6 +314,7 @@ enum optab_index
...
@@ -311,6 +314,7 @@ enum optab_index
/* Signed divide */
/* Signed divide */
OTI_sdiv
,
OTI_sdiv
,
OTI_sdivv
,
/* Signed divide-and-remainder in one */
/* Signed divide-and-remainder in one */
OTI_sdivmod
,
OTI_sdivmod
,
OTI_udiv
,
OTI_udiv
,
...
@@ -357,8 +361,10 @@ enum optab_index
...
@@ -357,8 +361,10 @@ enum optab_index
/* Unary operations */
/* Unary operations */
/* Negation */
/* Negation */
OTI_neg
,
OTI_neg
,
OTI_negv
,
/* Abs value */
/* Abs value */
OTI_abs
,
OTI_abs
,
OTI_absv
,
/* Bitwise not */
/* Bitwise not */
OTI_one_cmpl
,
OTI_one_cmpl
,
/* Find first bit set */
/* Find first bit set */
...
@@ -393,11 +399,15 @@ extern optab optab_table[OTI_MAX];
...
@@ -393,11 +399,15 @@ extern optab optab_table[OTI_MAX];
#define add_optab (optab_table[OTI_add])
#define add_optab (optab_table[OTI_add])
#define sub_optab (optab_table[OTI_sub])
#define sub_optab (optab_table[OTI_sub])
#define smul_optab (optab_table[OTI_smul])
#define smul_optab (optab_table[OTI_smul])
#define addv_optab (optab_table[OTI_addv])
#define subv_optab (optab_table[OTI_subv])
#define smul_highpart_optab (optab_table[OTI_smul_highpart])
#define smul_highpart_optab (optab_table[OTI_smul_highpart])
#define umul_highpart_optab (optab_table[OTI_umul_highpart])
#define umul_highpart_optab (optab_table[OTI_umul_highpart])
#define smul_widen_optab (optab_table[OTI_smul_widen])
#define smul_widen_optab (optab_table[OTI_smul_widen])
#define umul_widen_optab (optab_table[OTI_umul_widen])
#define umul_widen_optab (optab_table[OTI_umul_widen])
#define sdiv_optab (optab_table[OTI_sdiv])
#define sdiv_optab (optab_table[OTI_sdiv])
#define smulv_optab (optab_table[OTI_smulv])
#define sdivv_optab (optab_table[OTI_sdivv])
#define sdivmod_optab (optab_table[OTI_sdivmod])
#define sdivmod_optab (optab_table[OTI_sdivmod])
#define udiv_optab (optab_table[OTI_udiv])
#define udiv_optab (optab_table[OTI_udiv])
#define udivmod_optab (optab_table[OTI_udivmod])
#define udivmod_optab (optab_table[OTI_udivmod])
...
@@ -422,7 +432,9 @@ extern optab optab_table[OTI_MAX];
...
@@ -422,7 +432,9 @@ extern optab optab_table[OTI_MAX];
#define movstrict_optab (optab_table[OTI_movstrict])
#define movstrict_optab (optab_table[OTI_movstrict])
#define neg_optab (optab_table[OTI_neg])
#define neg_optab (optab_table[OTI_neg])
#define negv_optab (optab_table[OTI_negv])
#define abs_optab (optab_table[OTI_abs])
#define abs_optab (optab_table[OTI_abs])
#define absv_optab (optab_table[OTI_absv])
#define one_cmpl_optab (optab_table[OTI_one_cmpl])
#define one_cmpl_optab (optab_table[OTI_one_cmpl])
#define ffs_optab (optab_table[OTI_ffs])
#define ffs_optab (optab_table[OTI_ffs])
#define sqrt_optab (optab_table[OTI_sqrt])
#define sqrt_optab (optab_table[OTI_sqrt])
...
@@ -769,7 +781,7 @@ extern int expand_twoval_binop PARAMS ((optab, rtx, rtx, rtx, rtx, int));
...
@@ -769,7 +781,7 @@ extern int expand_twoval_binop PARAMS ((optab, rtx, rtx, rtx, rtx, int));
extern
rtx
expand_unop
PARAMS
((
enum
machine_mode
,
optab
,
rtx
,
rtx
,
int
));
extern
rtx
expand_unop
PARAMS
((
enum
machine_mode
,
optab
,
rtx
,
rtx
,
int
));
/* Expand the absolute value operation. */
/* Expand the absolute value operation. */
extern
rtx
expand_abs
PARAMS
((
enum
machine_mode
,
rtx
,
rtx
,
int
));
extern
rtx
expand_abs
PARAMS
((
enum
machine_mode
,
rtx
,
rtx
,
int
,
int
));
/* Expand the complex absolute value operation. */
/* Expand the complex absolute value operation. */
extern
rtx
expand_complex_abs
PARAMS
((
enum
machine_mode
,
rtx
,
rtx
,
int
));
extern
rtx
expand_complex_abs
PARAMS
((
enum
machine_mode
,
rtx
,
rtx
,
int
));
...
...
gcc/flags.h
View file @
91ce572a
...
@@ -555,6 +555,10 @@ extern int frame_pointer_needed;
...
@@ -555,6 +555,10 @@ extern int frame_pointer_needed;
extern
int
flag_check_memory_usage
;
extern
int
flag_check_memory_usage
;
/* Nonzero if the generated code should trap on signed overflow
for PLUS / SUB / MULT. */
extern
int
flag_trapv
;
/* Nonzero if GCC must prefix function names (used with
/* Nonzero if GCC must prefix function names (used with
flag_check_memory_usage). */
flag_check_memory_usage). */
...
...
gcc/genopinit.c
View file @
91ce572a
...
@@ -46,8 +46,11 @@ Boston, MA 02111-1307, USA. */
...
@@ -46,8 +46,11 @@ Boston, MA 02111-1307, USA. */
If $N is present in the pattern, it means the two modes must be consecutive
If $N is present in the pattern, it means the two modes must be consecutive
widths in the same mode class (e.g, QImode and HImode). $I means that
widths in the same mode class (e.g, QImode and HImode). $I means that
only integer modes should be considered for the next mode, and $F means
only full integer modes should be considered for the next mode, and $F
that only float modes should be considered.
means that only float modes should be considered.
$P means that both full and partial integer modes should be considered.
$V means to emit 'v' if the first mode is a MODE_FLOAT mode.
For some optabs, we store the operation by RTL codes. These are only
For some optabs, we store the operation by RTL codes. These are only
used for comparisons. In that case, $c and $C are the lower-case and
used for comparisons. In that case, $c and $C are the lower-case and
...
@@ -62,14 +65,24 @@ const char * const optabs[] =
...
@@ -62,14 +65,24 @@ const char * const optabs[] =
"fixtrunctab[$A][$B][1] = CODE_FOR_$(fixuns_trunc$F$a$I$b2$)"
,
"fixtrunctab[$A][$B][1] = CODE_FOR_$(fixuns_trunc$F$a$I$b2$)"
,
"floattab[$B][$A][0] = CODE_FOR_$(float$I$a$F$b2$)"
,
"floattab[$B][$A][0] = CODE_FOR_$(float$I$a$F$b2$)"
,
"floattab[$B][$A][1] = CODE_FOR_$(floatuns$I$a$F$b2$)"
,
"floattab[$B][$A][1] = CODE_FOR_$(floatuns$I$a$F$b2$)"
,
"add_optab->handlers[$A].insn_code = CODE_FOR_$(add$a3$)"
,
"add_optab->handlers[$A].insn_code = CODE_FOR_$(add$P$a3$)"
,
"sub_optab->handlers[$A].insn_code = CODE_FOR_$(sub$a3$)"
,
"addv_optab->handlers[(int) $A].insn_code =
\n
\
"smul_optab->handlers[$A].insn_code = CODE_FOR_$(mul$a3$)"
,
add_optab->handlers[(int) $A].insn_code = CODE_FOR_$(add$F$a3$)"
,
"addv_optab->handlers[(int) $A].insn_code = CODE_FOR_$(addv$I$a3$)"
,
"sub_optab->handlers[$A].insn_code = CODE_FOR_$(sub$P$a3$)"
,
"subv_optab->handlers[(int) $A].insn_code =
\n
\
sub_optab->handlers[(int) $A].insn_code = CODE_FOR_$(sub$F$a3$)"
,
"subv_optab->handlers[(int) $A].insn_code = CODE_FOR_$(subv$I$a3$)"
,
"smul_optab->handlers[$A].insn_code = CODE_FOR_$(mul$P$a3$)"
,
"smulv_optab->handlers[(int) $A].insn_code =
\n
\
smul_optab->handlers[(int) $A].insn_code = CODE_FOR_$(mul$F$a3$)"
,
"smulv_optab->handlers[(int) $A].insn_code = CODE_FOR_$(mulv$I$a3$)"
,
"umul_highpart_optab->handlers[$A].insn_code = CODE_FOR_$(umul$a3_highpart$)"
,
"umul_highpart_optab->handlers[$A].insn_code = CODE_FOR_$(umul$a3_highpart$)"
,
"smul_highpart_optab->handlers[$A].insn_code = CODE_FOR_$(smul$a3_highpart$)"
,
"smul_highpart_optab->handlers[$A].insn_code = CODE_FOR_$(smul$a3_highpart$)"
,
"smul_widen_optab->handlers[$B].insn_code = CODE_FOR_$(mul$a$b3$)$N"
,
"smul_widen_optab->handlers[$B].insn_code = CODE_FOR_$(mul$a$b3$)$N"
,
"umul_widen_optab->handlers[$B].insn_code = CODE_FOR_$(umul$a$b3$)$N"
,
"umul_widen_optab->handlers[$B].insn_code = CODE_FOR_$(umul$a$b3$)$N"
,
"sdiv_optab->handlers[$A].insn_code = CODE_FOR_$(div$I$a3$)"
,
"sdiv_optab->handlers[$A].insn_code = CODE_FOR_$(div$I$a3$)"
,
"sdivv_optab->handlers[(int) $A].insn_code = CODE_FOR_$(div$V$I$a3$)"
,
"udiv_optab->handlers[$A].insn_code = CODE_FOR_$(udiv$I$a3$)"
,
"udiv_optab->handlers[$A].insn_code = CODE_FOR_$(udiv$I$a3$)"
,
"sdivmod_optab->handlers[$A].insn_code = CODE_FOR_$(divmod$a4$)"
,
"sdivmod_optab->handlers[$A].insn_code = CODE_FOR_$(divmod$a4$)"
,
"udivmod_optab->handlers[$A].insn_code = CODE_FOR_$(udivmod$a4$)"
,
"udivmod_optab->handlers[$A].insn_code = CODE_FOR_$(udivmod$a4$)"
,
...
@@ -91,8 +104,14 @@ const char * const optabs[] =
...
@@ -91,8 +104,14 @@ const char * const optabs[] =
"smax_optab->handlers[$A].insn_code = CODE_FOR_$(max$F$a3$)"
,
"smax_optab->handlers[$A].insn_code = CODE_FOR_$(max$F$a3$)"
,
"umin_optab->handlers[$A].insn_code = CODE_FOR_$(umin$I$a3$)"
,
"umin_optab->handlers[$A].insn_code = CODE_FOR_$(umin$I$a3$)"
,
"umax_optab->handlers[$A].insn_code = CODE_FOR_$(umax$I$a3$)"
,
"umax_optab->handlers[$A].insn_code = CODE_FOR_$(umax$I$a3$)"
,
"neg_optab->handlers[$A].insn_code = CODE_FOR_$(neg$a2$)"
,
"neg_optab->handlers[$A].insn_code = CODE_FOR_$(neg$P$a2$)"
,
"abs_optab->handlers[$A].insn_code = CODE_FOR_$(abs$a2$)"
,
"negv_optab->handlers[(int) $A].insn_code =
\n
\
neg_optab->handlers[(int) $A].insn_code = CODE_FOR_$(neg$F$a2$)"
,
"negv_optab->handlers[(int) $A].insn_code = CODE_FOR_$(negv$I$a2$)"
,
"abs_optab->handlers[$A].insn_code = CODE_FOR_$(abs$P$a2$)"
,
"absv_optab->handlers[(int) $A].insn_code =
\n
\
abs_optab->handlers[(int) $A].insn_code = CODE_FOR_$(abs$F$a2$)"
,
"absv_optab->handlers[(int) $A].insn_code = CODE_FOR_$(absv$I$a2$)"
,
"sqrt_optab->handlers[$A].insn_code = CODE_FOR_$(sqrt$a2$)"
,
"sqrt_optab->handlers[$A].insn_code = CODE_FOR_$(sqrt$a2$)"
,
"sin_optab->handlers[$A].insn_code = CODE_FOR_$(sin$a2$)"
,
"sin_optab->handlers[$A].insn_code = CODE_FOR_$(sin$a2$)"
,
"cos_optab->handlers[$A].insn_code = CODE_FOR_$(cos$a2$)"
,
"cos_optab->handlers[$A].insn_code = CODE_FOR_$(cos$a2$)"
,
...
@@ -136,7 +155,7 @@ gen_insn (insn)
...
@@ -136,7 +155,7 @@ gen_insn (insn)
for
(
pindex
=
0
;
pindex
<
ARRAY_SIZE
(
optabs
);
pindex
++
)
for
(
pindex
=
0
;
pindex
<
ARRAY_SIZE
(
optabs
);
pindex
++
)
{
{
int
force_float
=
0
,
force_int
=
0
;
int
force_float
=
0
,
force_int
=
0
,
force_partial_int
=
0
;
int
force_consec
=
0
;
int
force_consec
=
0
;
int
matches
=
1
;
int
matches
=
1
;
...
@@ -160,9 +179,14 @@ gen_insn (insn)
...
@@ -160,9 +179,14 @@ gen_insn (insn)
case
'I'
:
case
'I'
:
force_int
=
1
;
force_int
=
1
;
break
;
break
;
case
'P'
:
force_partial_int
=
1
;
break
;
case
'F'
:
case
'F'
:
force_float
=
1
;
force_float
=
1
;
break
;
break
;
case
'V'
:
break
;
case
'c'
:
case
'c'
:
for
(
op
=
0
;
op
<
NUM_RTX_CODE
;
op
++
)
for
(
op
=
0
;
op
<
NUM_RTX_CODE
;
op
++
)
{
{
...
@@ -196,6 +220,9 @@ gen_insn (insn)
...
@@ -196,6 +220,9 @@ gen_insn (insn)
if
(
*
p
==
0
if
(
*
p
==
0
&&
(
!
force_int
||
mode_class
[
i
]
==
MODE_INT
)
&&
(
!
force_int
||
mode_class
[
i
]
==
MODE_INT
)
&&
(
!
force_partial_int
||
mode_class
[
i
]
==
MODE_INT
||
mode_class
[
i
]
==
MODE_PARTIAL_INT
)
&&
(
!
force_float
||
mode_class
[
i
]
==
MODE_FLOAT
))
&&
(
!
force_float
||
mode_class
[
i
]
==
MODE_FLOAT
))
break
;
break
;
}
}
...
@@ -207,7 +234,7 @@ gen_insn (insn)
...
@@ -207,7 +234,7 @@ gen_insn (insn)
else
else
m2
=
i
,
np
+=
strlen
(
GET_MODE_NAME
(
i
));
m2
=
i
,
np
+=
strlen
(
GET_MODE_NAME
(
i
));
force_int
=
force_float
=
0
;
force_int
=
force_
partial_int
=
force_
float
=
0
;
break
;
break
;
default
:
default
:
...
@@ -243,6 +270,10 @@ gen_insn (insn)
...
@@ -243,6 +270,10 @@ gen_insn (insn)
case
'('
:
case
')'
:
case
'('
:
case
')'
:
case
'I'
:
case
'F'
:
case
'N'
:
case
'I'
:
case
'F'
:
case
'N'
:
break
;
break
;
case
'V'
:
if
(
GET_MODE_CLASS
(
m1
)
==
MODE_FLOAT
)
printf
(
"v"
);
break
;
case
'a'
:
case
'a'
:
for
(
np
=
GET_MODE_NAME
(
m1
);
*
np
;
np
++
)
for
(
np
=
GET_MODE_NAME
(
m1
);
*
np
;
np
++
)
putchar
(
TOLOWER
(
*
np
));
putchar
(
TOLOWER
(
*
np
));
...
...
gcc/invoke.texi
View file @
91ce572a
...
@@ -173,7 +173,7 @@ in the following sections.
...
@@ -173,7 +173,7 @@ in the following sections.
-fdata-sections -ffunction-sections -fgcse
-fdata-sections -ffunction-sections -fgcse
-finline-functions -finline-limit=@var{n} -fkeep-inline-functions
-finline-functions -finline-limit=@var{n} -fkeep-inline-functions
-fmove-all-movables -fno-default-inline -fno-defer-pop
-fmove-all-movables -fno-default-inline -fno-defer-pop
-fno-function-cse -fno-inline -fno-peephole
-fno-function-cse -fno-inline -fno-peephole
-ftrapv
-fomit-frame-pointer -foptimize-register-moves -foptimize-sibling-calls
-fomit-frame-pointer -foptimize-register-moves -foptimize-sibling-calls
-fregmove -frerun-cse-after-loop -frerun-loop-opt -freduce-all-givs
-fregmove -frerun-cse-after-loop -frerun-loop-opt -freduce-all-givs
-fschedule-insns -fschedule-insns2 -fssa -fstrength-reduce
-fschedule-insns -fschedule-insns2 -fssa -fstrength-reduce
...
@@ -2664,6 +2664,10 @@ Usage, gcc.info, Using and Porting GCC}.@refill
...
@@ -2664,6 +2664,10 @@ Usage, gcc.info, Using and Porting GCC}.@refill
@
item
-
foptimize
-
sibling
-
calls
@
item
-
foptimize
-
sibling
-
calls
Optimize
sibling
and
tail
recursive
calls
.
Optimize
sibling
and
tail
recursive
calls
.
@
item
-
ftrapv
This
option
generates
traps
for
signed
overflow
on
addition
,
subtraction
,
multiplication
operations
.
@
item
-
fno
-
inline
@
item
-
fno
-
inline
Don
't pay attention to the @code{inline} keyword. Normally this option
Don
't pay attention to the @code{inline} keyword. Normally this option
is used to keep the compiler from expanding any functions inline.
is used to keep the compiler from expanding any functions inline.
...
...
gcc/libgcc2.c
View file @
91ce572a
...
@@ -50,6 +50,176 @@ Boston, MA 02111-1307, USA. */
...
@@ -50,6 +50,176 @@ Boston, MA 02111-1307, USA. */
#if defined (L_divdi3) || defined (L_moddi3)
#if defined (L_divdi3) || defined (L_moddi3)
static
inline
static
inline
#endif
#endif
#ifdef L_addvsi3
SItype
__addvsi3
(
SItype
a
,
SItype
b
)
{
SItype
w
,
w1
;
w
=
a
+
b
;
if
(
b
>=
0
?
w
<
a
:
w
>
a
)
abort
();
return
w
;
}
#ifdef L_addvdi3
DItype
__addvdi3
(
DItype
a
,
DItype
b
)
{
DItype
w
;
w
=
a
+
b
;
if
(
b
>=
0
?
w
<
a
:
w
>
a
)
abort
();
return
w
;
}
#endif
#ifdef L_subvsi3
SItype
__subvsi3
(
SItype
a
,
SItype
b
)
{
#ifdef L_addvsi3
return
__addvsi3
(
a
,
(
-
b
));
#else
DItype
w
;
w
=
a
-
b
;
if
(
b
>=
0
?
w
>
a
:
w
<
a
)
abort
();
return
w
;
#endif
}
#endif
#ifdef L_subvdi3
DItype
__subvdi3
(
DItype
a
,
DItype
b
)
{
#ifdef L_addvdi3
return
(
a
,
(
-
b
));
#else
DItype
w
;
w
=
a
-
b
;
if
(
b
>=
0
?
w
>
a
:
w
<
a
)
abort
();
return
w
;
#endif
}
#endif
#ifdef L_mulvsi3
SItype
__mulvsi3
(
SItype
a
,
SItype
b
)
{
DItype
w
;
w
=
a
*
b
;
if
((
a
>=
0
&&
b
>=
0
)
?
w
<
0
:
(
a
>=
0
||
b
>=
0
)
?
w
>
0
:
w
<
0
)
abort
();
return
w
;
}
#endif
#ifdef L_negvsi2
SItype
__negvsi2
(
SItype
a
)
{
SItype
w
;
w
=
-
a
;
if
(
a
>=
0
?
w
>
0
:
w
<
0
)
abort
();
return
w
;
}
#endif
#ifdef L_negvdi2
DItype
__negvdi2
(
DItype
a
)
{
DItype
w
;
w
=
-
a
;
if
(
a
>=
0
?
w
>
0
:
w
<
0
)
abort
();
return
w
;
}
#endif
#ifdef L_absvsi2
SItype
__absvsi2
(
SItype
a
)
{
SItype
w
=
a
;
if
(
a
<
0
)
#ifdef L_negvsi2
w
=
__negvsi2
(
a
);
#else
w
=
-
a
;
if
(
w
<
0
)
abort
();
#endif
return
w
;
}
#endif
#ifdef L_absvdi2
DItype
__absvdi2
(
DItype
a
)
{
DItype
w
=
a
;
if
(
a
<
0
)
#ifdef L_negvsi2
w
=
__negvsi2
(
a
);
#else
w
=
-
a
;
if
(
w
<
0
)
abort
();
#endif
return
w
;
}
#endif
#ifdef L_mulvdi3
DItype
__mulvdi3
(
DItype
u
,
DItype
v
)
{
DItype
w
;
w
=
u
*
v
;
if
((
u
>=
0
&&
v
>=
0
)
?
w
<
0
:
(
u
>=
0
||
v
>=
0
)
?
w
>
0
:
w
<
0
)
abort
();
return
w
;
}
#endif
DWtype
DWtype
__negdi2
(
DWtype
u
)
__negdi2
(
DWtype
u
)
{
{
...
...
gcc/loop.c
View file @
91ce572a
...
@@ -6877,7 +6877,7 @@ emit_iv_add_mult (b, m, a, reg, insert_before)
...
@@ -6877,7 +6877,7 @@ emit_iv_add_mult (b, m, a, reg, insert_before)
update_reg_last_use
(
m
,
insert_before
);
update_reg_last_use
(
m
,
insert_before
);
start_sequence
();
start_sequence
();
result
=
expand_mult_add
(
b
,
reg
,
m
,
a
,
GET_MODE
(
reg
),
0
);
result
=
expand_mult_add
(
b
,
reg
,
m
,
a
,
GET_MODE
(
reg
),
1
);
if
(
reg
!=
result
)
if
(
reg
!=
result
)
emit_move_insn
(
reg
,
result
);
emit_move_insn
(
reg
,
result
);
seq
=
gen_sequence
();
seq
=
gen_sequence
();
...
@@ -6961,7 +6961,7 @@ product_cheap_p (a, b)
...
@@ -6961,7 +6961,7 @@ product_cheap_p (a, b)
of insns is generated. */
of insns is generated. */
start_sequence
();
start_sequence
();
expand_mult
(
GET_MODE
(
a
),
a
,
b
,
NULL_RTX
,
0
);
expand_mult
(
GET_MODE
(
a
),
a
,
b
,
NULL_RTX
,
1
);
tmp
=
gen_sequence
();
tmp
=
gen_sequence
();
end_sequence
();
end_sequence
();
...
...
gcc/optabs.c
View file @
91ce572a
This diff is collapsed.
Click to expand it.
gcc/toplev.c
View file @
91ce572a
...
@@ -947,6 +947,8 @@ typedef struct
...
@@ -947,6 +947,8 @@ typedef struct
}
}
lang_independent_options
;
lang_independent_options
;
int
flag_trapv
=
0
;
/* Add or remove a leading underscore from user symbols. */
/* Add or remove a leading underscore from user symbols. */
int
flag_leading_underscore
=
-
1
;
int
flag_leading_underscore
=
-
1
;
...
@@ -1145,6 +1147,8 @@ lang_independent_options f_options[] =
...
@@ -1145,6 +1147,8 @@ lang_independent_options f_options[] =
"Report time taken by each compiler pass at end of run"
},
"Report time taken by each compiler pass at end of run"
},
{
"mem-report"
,
&
mem_report
,
1
,
{
"mem-report"
,
&
mem_report
,
1
,
"Report on permanent memory allocation at end of run"
},
"Report on permanent memory allocation at end of run"
},
{
"trapv"
,
&
flag_trapv
,
1
,
"Trap for signed overflow in addition / subtraction / multiplication."
},
};
};
/* Table of language-specific options. */
/* Table of language-specific options. */
...
...
gcc/tree.h
View file @
91ce572a
...
@@ -574,6 +574,8 @@ extern void tree_class_check_failed PARAMS ((const tree, int,
...
@@ -574,6 +574,8 @@ extern void tree_class_check_failed PARAMS ((const tree, int,
The same bit is used in functions as DECL_BUILT_IN_NONANSI. */
The same bit is used in functions as DECL_BUILT_IN_NONANSI. */
#define TREE_UNSIGNED(NODE) ((NODE)->common.unsigned_flag)
#define TREE_UNSIGNED(NODE) ((NODE)->common.unsigned_flag)
#define TYPE_TRAP_SIGNED(NODE) (flag_trapv && ! TREE_UNSIGNED (NODE))
/* Nonzero in a VAR_DECL means assembler code has been written.
/* Nonzero in a VAR_DECL means assembler code has been written.
Nonzero in a FUNCTION_DECL means that the function has been compiled.
Nonzero in a FUNCTION_DECL means that the function has been compiled.
This is interesting in an inline function, since it might not need
This is interesting in an inline function, since it might not need
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment