diff options
author | chaoyingfu <chaoyingfu@138bc75d-0d04-0410-961f-82ee72b054a4> | 2007-08-30 23:09:28 +0000 |
---|---|---|
committer | chaoyingfu <chaoyingfu@138bc75d-0d04-0410-961f-82ee72b054a4> | 2007-08-30 23:09:28 +0000 |
commit | b563b483b9f482b0ebd10d79d5982fb6eb3653d7 (patch) | |
tree | 147d8f8e5f66c5b18b1af215b5ed27814c9a27a1 /gcc/c-lex.c | |
parent | 84373723043bc16686594a725911ed92be41db24 (diff) | |
download | ppe42-gcc-b563b483b9f482b0ebd10d79d5982fb6eb3653d7.tar.gz ppe42-gcc-b563b483b9f482b0ebd10d79d5982fb6eb3653d7.zip |
* c-lex.c (interpret_fixed): Declare.
(interpret_float): Process _Fract and _Accum.
(interpret_fixed): New function.
* final.c (output_addr_const): Process CONST_FIXED.
* simplify-rtx.c (simplify_const_unary_operation): Handle US_NEG.
(simplify_binary_operation_1): Handle US_ASHIFT, SS_MULT, US_MULT,
SS_DIV, US_DIV.
(simplify_const_binary_operation): Handle SS_MULT, US_MULT, SS_DIV,
US_DIV, US_ASHIFT.
(simplify_immed_subreg): Support CONST_FIXED.
Process MODE_FRACT, MODE_UFRACT, MODE_ACCUM, MODE_UACCUM.
(simplify_subreg): Support CONST_FIXED.
git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/trunk@127941 138bc75d-0d04-0410-961f-82ee72b054a4
Diffstat (limited to 'gcc/c-lex.c')
-rw-r--r-- | gcc/c-lex.c | 130 |
1 files changed, 130 insertions, 0 deletions
diff --git a/gcc/c-lex.c b/gcc/c-lex.c index a4e3b0c8094..17cb9ed5e22 100644 --- a/gcc/c-lex.c +++ b/gcc/c-lex.c @@ -61,6 +61,7 @@ bool c_lex_return_raw_strings = false; static tree interpret_integer (const cpp_token *, unsigned int); static tree interpret_float (const cpp_token *, unsigned int); +static tree interpret_fixed (const cpp_token *, unsigned int); static enum integer_type_kind narrowest_unsigned_type (unsigned HOST_WIDE_INT, unsigned HOST_WIDE_INT, unsigned int); static enum integer_type_kind narrowest_signed_type @@ -640,6 +641,10 @@ interpret_float (const cpp_token *token, unsigned int flags) char *copy; size_t copylen; + /* Decode _Fract and _Accum. */ + if (flags & CPP_N_FRACT || flags & CPP_N_ACCUM) + return interpret_fixed (token, flags); + /* Decode type based on width and properties. */ if (flags & CPP_N_DFLOAT) if ((flags & CPP_N_WIDTH) == CPP_N_LARGE) @@ -731,6 +736,131 @@ interpret_float (const cpp_token *token, unsigned int flags) return value; } +/* Interpret TOKEN, a fixed-point number with FLAGS as classified + by cpplib. */ + +static tree +interpret_fixed (const cpp_token *token, unsigned int flags) +{ + tree type; + tree value; + FIXED_VALUE_TYPE fixed; + char *copy; + size_t copylen; + + copylen = token->val.str.len; + + if (flags & CPP_N_FRACT) /* _Fract. */ + { + if (flags & CPP_N_UNSIGNED) /* Unsigned _Fract. */ + { + if ((flags & CPP_N_WIDTH) == CPP_N_LARGE) + { + type = unsigned_long_long_fract_type_node; + copylen -= 4; + } + else if ((flags & CPP_N_WIDTH) == CPP_N_MEDIUM) + { + type = unsigned_long_fract_type_node; + copylen -= 3; + } + else if ((flags & CPP_N_WIDTH) == CPP_N_SMALL) + { + type = unsigned_short_fract_type_node; + copylen -= 3; + } + else + { + type = unsigned_fract_type_node; + copylen -= 2; + } + } + else /* Signed _Fract. */ + { + if ((flags & CPP_N_WIDTH) == CPP_N_LARGE) + { + type = long_long_fract_type_node; + copylen -= 3; + } + else if ((flags & CPP_N_WIDTH) == CPP_N_MEDIUM) + { + type = long_fract_type_node; + copylen -= 2; + } + else if ((flags & CPP_N_WIDTH) == CPP_N_SMALL) + { + type = short_fract_type_node; + copylen -= 2; + } + else + { + type = fract_type_node; + copylen --; + } + } + } + else /* _Accum. */ + { + if (flags & CPP_N_UNSIGNED) /* Unsigned _Accum. */ + { + if ((flags & CPP_N_WIDTH) == CPP_N_LARGE) + { + type = unsigned_long_long_accum_type_node; + copylen -= 4; + } + else if ((flags & CPP_N_WIDTH) == CPP_N_MEDIUM) + { + type = unsigned_long_accum_type_node; + copylen -= 3; + } + else if ((flags & CPP_N_WIDTH) == CPP_N_SMALL) + { + type = unsigned_short_accum_type_node; + copylen -= 3; + } + else + { + type = unsigned_accum_type_node; + copylen -= 2; + } + } + else /* Signed _Accum. */ + { + if ((flags & CPP_N_WIDTH) == CPP_N_LARGE) + { + type = long_long_accum_type_node; + copylen -= 3; + } + else if ((flags & CPP_N_WIDTH) == CPP_N_MEDIUM) + { + type = long_accum_type_node; + copylen -= 2; + } + else if ((flags & CPP_N_WIDTH) == CPP_N_SMALL) + { + type = short_accum_type_node; + copylen -= 2; + } + else + { + type = accum_type_node; + copylen --; + } + } + } + + copy = (char *) alloca (copylen + 1); + memcpy (copy, token->val.str.text, copylen); + copy[copylen] = '\0'; + + fixed_from_string (&fixed, copy, TYPE_MODE (type)); + + /* Create a node with determined type and value. */ + value = build_fixed (type, fixed); + + return value; +} + /* Convert a series of STRING and/or WSTRING tokens into a tree, performing string constant concatenation. TOK is the first of these. VALP is the location to write the string into. OBJC_STRING |