machmode.h (int_n_data_t): New.

* machmode.h (int_n_data_t): New.
	(int_n_enabled_p): New.
	(int_n_data): New.
	* tree.c (int_n_enabled_p): New.
	(int_n_trees): New.
	(make_or_reuse_type): Check for all __intN types, not just
	__int128.
	(build_common_tree_nodes): Likewise.  Also fill in integer_typs[]
	entries.
	* tree.h (int128_integer_type_node): Remove.
	(int128_unsigned_type_node): Remove.
	(int_n_trees_t): New.
	(int_n_enabled_p): New.
	(int_n_trees): New.
	* toplev.c (standard_type_bitsize): New.
	(do_compile): Check which __intN types are enabled for the current
	run.
	* builtin-types.def (BT_INT128): Remove.
	(BT_UINT128): Remove.
	* machmode.def: Add macro to create __int128 for all targets.
	* stor-layout.c (mode_for_size): Support __intN types.
	(smallest_mode_for_size): Likewise.
	(initialize_sizetypes): Support __intN types.
	* genmodes.c (struct mode_data): Add int_n field.
	(blank_mode): Likewise.
	(INT_N): New.
	(make_int_n): New.
	(emit_insn_modes_h): Count __intN entries and define
	NUM_INT_N_ENTS.
	(emit_mode_int_n): New.
	(emit_insn_modes_c): Call it.
	* gimple.c (gimple_signed_or_unsigned_type): Check for all __intN
	types, not just __int128.
	* tree-core.h (integer_type_kind): Remove __int128-specific
	entries, reserve spots for __intN entries.

libstdc++-v3/
	* src/c++11/limits.cc: Add support for __intN types.
	* include/std/type_traits: Likewise.
	* include/std/limits: Likewise.
	* include/c_std/cstdlib: Likewise.
	* include/bits/cpp_type_traits.h: Likewise.
	* include/c_global/cstdlib: Likewise.

c-family/
	* c-pretty-print.c (pp_c_integer_constant): Check for all __intN
	types, not just __int128.
	* c-cppbuiltin.c (c_cpp_builtins): Add builtins for all __intN
	types, not just __int128.
	(cpp_atomic_builtins): Round pointer sizes up.
	(type_suffix): Use type precision, not specific types.
	* c-common.c (c_common_reswords): Remove __int128 special case.
	(c_common_type_for_size): Check for all __intN types, not just
	__int128.
	(c_common_type_for_mode): Likewise.
	(c_common_signed_or_unsigned_type): Likewise.
	(c_build_bitfield_integer_type): Likewise.
	(c_common_nodes_and_builtins): Likewise.
	(keyword_begins_type_specifier): Likewise.
	* c-common.h (rid): Remove RID_INT128 and add RID_INT_N_* for all
	__intN variants.

c/
	* c-parser.c (c_parse_init): Add RID entries for each __intN.
	(c_token_starts_typename): Check all __intN, not just __int128.
	(c_token_starts_declspecs): Likewise.
	(c_parser_declspecs): Likewise.
	(c_parser_attribute_any_word): Likewise.
	(c_parser_objc_selector): Likewise.
	* c-tree.h (c_typespec_keyword): cts_int128 -> cts_int_n.
	(struct c_declspecs): Add int_n_idx field to record *which* __intN
	is specified.
	* c-decl.c (declspecs_add_type): Check for all __intN, not just
	__int128.
	(finish_declspecs): Likewise.

testsuite/
	* g++.dg/abi/mangle64.C: New.

cp/
	* typeck.c (cp_common_type): Check for all __intN types, not just
	__int128.
	* decl.c (grokdeclarator): Likewise.
	* rtti.c (emit_support_tinfos): Check for all __intN types, not just
	__int128.
	* parser.c (cp_lexer_next_token_is_decl_specifier_keyword): Check
	for all __intN types, not just __int128.
	(cp_parser_simple_type_specifier): Likewise.
	* mangle.c (integer_type_codes): Remove int128-specific codes.
	* cp-tree.h (cp_decl_specifier_seq): Add int_n_idx to store which
	__intN was specified.
	* lex.c (init_reswords): Reserve all __intN keywords.

lto/
	* lto-lang.c (lto_build_c_type_nodes): Check intN types for
	size-type as well.
	(lto_init): Initialize all intN types, not just int128.

From-SVN: r216220
This commit is contained in:
DJ Delorie 2014-10-14 15:44:36 -04:00 committed by DJ Delorie
parent df3e34938d
commit 78a7c3172f
39 changed files with 1041 additions and 353 deletions

View File

@ -1,3 +1,43 @@
2014-10-14 DJ Delorie <dj@redhat.com>
* machmode.h (int_n_data_t): New.
(int_n_enabled_p): New.
(int_n_data): New.
* tree.c (int_n_enabled_p): New.
(int_n_trees): New.
(make_or_reuse_type): Check for all __intN types, not just
__int128.
(build_common_tree_nodes): Likewise. Also fill in integer_typs[]
entries.
* tree.h (int128_integer_type_node): Remove.
(int128_unsigned_type_node): Remove.
(int_n_trees_t): New.
(int_n_enabled_p): New.
(int_n_trees): New.
* toplev.c (standard_type_bitsize): New.
(do_compile): Check which __intN types are enabled for the current
run.
* builtin-types.def (BT_INT128): Remove.
(BT_UINT128): Remove.
* machmode.def: Add macro to create __int128 for all targets.
* stor-layout.c (mode_for_size): Support __intN types.
(smallest_mode_for_size): Likewise.
(initialize_sizetypes): Support __intN types.
* genmodes.c (struct mode_data): Add int_n field.
(blank_mode): Likewise.
(INT_N): New.
(make_int_n): New.
(emit_insn_modes_h): Count __intN entries and define
NUM_INT_N_ENTS.
(emit_mode_int_n): New.
(emit_insn_modes_c): Call it.
* gimple.c (gimple_signed_or_unsigned_type): Check for all __intN
types, not just __int128.
* tree-core.h (integer_type_kind): Remove __int128-specific
entries, reserve spots for __intN entries.
* config/msp430/msp430-modes.def (PSI): Add.
2014-10-14 Kito Cheng <kito@0xlab.org> 2014-10-14 Kito Cheng <kito@0xlab.org>
* ira.c: Fix typo in comment. * ira.c: Fix typo in comment.

View File

@ -65,8 +65,6 @@ DEF_PRIMITIVE_TYPE (BT_LONG, long_integer_type_node)
DEF_PRIMITIVE_TYPE (BT_ULONG, long_unsigned_type_node) DEF_PRIMITIVE_TYPE (BT_ULONG, long_unsigned_type_node)
DEF_PRIMITIVE_TYPE (BT_LONGLONG, long_long_integer_type_node) DEF_PRIMITIVE_TYPE (BT_LONGLONG, long_long_integer_type_node)
DEF_PRIMITIVE_TYPE (BT_ULONGLONG, long_long_unsigned_type_node) DEF_PRIMITIVE_TYPE (BT_ULONGLONG, long_long_unsigned_type_node)
DEF_PRIMITIVE_TYPE (BT_INT128, int128_integer_type_node)
DEF_PRIMITIVE_TYPE (BT_UINT128, int128_unsigned_type_node)
DEF_PRIMITIVE_TYPE (BT_INTMAX, intmax_type_node) DEF_PRIMITIVE_TYPE (BT_INTMAX, intmax_type_node)
DEF_PRIMITIVE_TYPE (BT_UINTMAX, uintmax_type_node) DEF_PRIMITIVE_TYPE (BT_UINTMAX, uintmax_type_node)
DEF_PRIMITIVE_TYPE (BT_UINT16, uint16_type_node) DEF_PRIMITIVE_TYPE (BT_UINT16, uint16_type_node)

View File

@ -1,3 +1,22 @@
2014-10-14 DJ Delorie <dj@redhat.com>
* c-pretty-print.c (pp_c_integer_constant): Check for all __intN
types, not just __int128.
* c-cppbuiltin.c (c_cpp_builtins): Add builtins for all __intN
types, not just __int128.
(cpp_atomic_builtins): Round pointer sizes up.
(type_suffix): Use type precision, not specific types.
* c-common.c (c_common_reswords): Remove __int128 special case.
(c_common_type_for_size): Check for all __intN types, not just
__int128.
(c_common_type_for_mode): Likewise.
(c_common_signed_or_unsigned_type): Likewise.
(c_build_bitfield_integer_type): Likewise.
(c_common_nodes_and_builtins): Likewise.
(keyword_begins_type_specifier): Likewise.
* c-common.h (rid): Remove RID_INT128 and add RID_INT_N_* for all
__intN variants.
2014-10-12 Trevor Saunders <tsaunders@mozilla.com> 2014-10-12 Trevor Saunders <tsaunders@mozilla.com>
* c-common.c: Use hash_table instead of hashtab. * c-common.c: Use hash_table instead of hashtab.

View File

@ -61,12 +61,10 @@ cpp_reader *parse_in; /* Declared in c-pragma.h. */
tree short_integer_type_node; tree short_integer_type_node;
tree long_integer_type_node; tree long_integer_type_node;
tree long_long_integer_type_node; tree long_long_integer_type_node;
tree int128_integer_type_node;
tree short_unsigned_type_node; tree short_unsigned_type_node;
tree long_unsigned_type_node; tree long_unsigned_type_node;
tree long_long_unsigned_type_node; tree long_long_unsigned_type_node;
tree int128_unsigned_type_node;
tree truthvalue_type_node; tree truthvalue_type_node;
tree truthvalue_false_node; tree truthvalue_false_node;
@ -468,7 +466,6 @@ const struct c_common_resword c_common_reswords[] =
{ "__imag__", RID_IMAGPART, 0 }, { "__imag__", RID_IMAGPART, 0 },
{ "__inline", RID_INLINE, 0 }, { "__inline", RID_INLINE, 0 },
{ "__inline__", RID_INLINE, 0 }, { "__inline__", RID_INLINE, 0 },
{ "__int128", RID_INT128, 0 },
{ "__is_abstract", RID_IS_ABSTRACT, D_CXXONLY }, { "__is_abstract", RID_IS_ABSTRACT, D_CXXONLY },
{ "__is_base_of", RID_IS_BASE_OF, D_CXXONLY }, { "__is_base_of", RID_IS_BASE_OF, D_CXXONLY },
{ "__is_class", RID_IS_CLASS, D_CXXONLY }, { "__is_class", RID_IS_CLASS, D_CXXONLY },
@ -3449,6 +3446,8 @@ check_case_bounds (location_t loc, tree type, tree orig_type,
tree tree
c_common_type_for_size (unsigned int bits, int unsignedp) c_common_type_for_size (unsigned int bits, int unsignedp)
{ {
int i;
if (bits == TYPE_PRECISION (integer_type_node)) if (bits == TYPE_PRECISION (integer_type_node))
return unsignedp ? unsigned_type_node : integer_type_node; return unsignedp ? unsigned_type_node : integer_type_node;
@ -3465,10 +3464,11 @@ c_common_type_for_size (unsigned int bits, int unsignedp)
return (unsignedp ? long_long_unsigned_type_node return (unsignedp ? long_long_unsigned_type_node
: long_long_integer_type_node); : long_long_integer_type_node);
if (int128_integer_type_node for (i = 0; i < NUM_INT_N_ENTS; i ++)
&& bits == TYPE_PRECISION (int128_integer_type_node)) if (int_n_enabled_p[i]
return (unsignedp ? int128_unsigned_type_node && bits == int_n_data[i].bitsize)
: int128_integer_type_node); return (unsignedp ? int_n_trees[i].unsigned_type
: int_n_trees[i].signed_type);
if (bits == TYPE_PRECISION (widest_integer_literal_type_node)) if (bits == TYPE_PRECISION (widest_integer_literal_type_node))
return (unsignedp ? widest_unsigned_literal_type_node return (unsignedp ? widest_unsigned_literal_type_node
@ -3532,6 +3532,7 @@ tree
c_common_type_for_mode (enum machine_mode mode, int unsignedp) c_common_type_for_mode (enum machine_mode mode, int unsignedp)
{ {
tree t; tree t;
int i;
if (mode == TYPE_MODE (integer_type_node)) if (mode == TYPE_MODE (integer_type_node))
return unsignedp ? unsigned_type_node : integer_type_node; return unsignedp ? unsigned_type_node : integer_type_node;
@ -3548,9 +3549,11 @@ c_common_type_for_mode (enum machine_mode mode, int unsignedp)
if (mode == TYPE_MODE (long_long_integer_type_node)) if (mode == TYPE_MODE (long_long_integer_type_node))
return unsignedp ? long_long_unsigned_type_node : long_long_integer_type_node; return unsignedp ? long_long_unsigned_type_node : long_long_integer_type_node;
if (int128_integer_type_node for (i = 0; i < NUM_INT_N_ENTS; i ++)
&& mode == TYPE_MODE (int128_integer_type_node)) if (int_n_enabled_p[i]
return unsignedp ? int128_unsigned_type_node : int128_integer_type_node; && mode == int_n_data[i].m)
return (unsignedp ? int_n_trees[i].unsigned_type
: int_n_trees[i].signed_type);
if (mode == TYPE_MODE (widest_integer_literal_type_node)) if (mode == TYPE_MODE (widest_integer_literal_type_node))
return unsignedp ? widest_unsigned_literal_type_node return unsignedp ? widest_unsigned_literal_type_node
@ -3748,6 +3751,7 @@ tree
c_common_signed_or_unsigned_type (int unsignedp, tree type) c_common_signed_or_unsigned_type (int unsignedp, tree type)
{ {
tree type1; tree type1;
int i;
/* This block of code emulates the behavior of the old /* This block of code emulates the behavior of the old
c_common_unsigned_type. In particular, it returns c_common_unsigned_type. In particular, it returns
@ -3766,10 +3770,14 @@ c_common_signed_or_unsigned_type (int unsignedp, tree type)
return unsignedp ? long_unsigned_type_node : long_integer_type_node; return unsignedp ? long_unsigned_type_node : long_integer_type_node;
if (type1 == long_long_integer_type_node || type1 == long_long_unsigned_type_node) if (type1 == long_long_integer_type_node || type1 == long_long_unsigned_type_node)
return unsignedp ? long_long_unsigned_type_node : long_long_integer_type_node; return unsignedp ? long_long_unsigned_type_node : long_long_integer_type_node;
if (int128_integer_type_node
&& (type1 == int128_integer_type_node for (i = 0; i < NUM_INT_N_ENTS; i ++)
|| type1 == int128_unsigned_type_node)) if (int_n_enabled_p[i]
return unsignedp ? int128_unsigned_type_node : int128_integer_type_node; && (type1 == int_n_trees[i].unsigned_type
|| type1 == int_n_trees[i].signed_type))
return (unsignedp ? int_n_trees[i].unsigned_type
: int_n_trees[i].signed_type);
if (type1 == widest_integer_literal_type_node || type1 == widest_unsigned_literal_type_node) if (type1 == widest_integer_literal_type_node || type1 == widest_unsigned_literal_type_node)
return unsignedp ? widest_unsigned_literal_type_node : widest_integer_literal_type_node; return unsignedp ? widest_unsigned_literal_type_node : widest_integer_literal_type_node;
#if HOST_BITS_PER_WIDE_INT >= 64 #if HOST_BITS_PER_WIDE_INT >= 64
@ -3884,9 +3892,14 @@ c_common_signed_or_unsigned_type (int unsignedp, tree type)
if (TYPE_OK (long_long_integer_type_node)) if (TYPE_OK (long_long_integer_type_node))
return (unsignedp ? long_long_unsigned_type_node return (unsignedp ? long_long_unsigned_type_node
: long_long_integer_type_node); : long_long_integer_type_node);
if (int128_integer_type_node && TYPE_OK (int128_integer_type_node))
return (unsignedp ? int128_unsigned_type_node for (i = 0; i < NUM_INT_N_ENTS; i ++)
: int128_integer_type_node); if (int_n_enabled_p[i]
&& TYPE_MODE (type) == int_n_data[i].m
&& TYPE_PRECISION (type) == int_n_data[i].bitsize)
return (unsignedp ? int_n_trees[i].unsigned_type
: int_n_trees[i].signed_type);
if (TYPE_OK (widest_integer_literal_type_node)) if (TYPE_OK (widest_integer_literal_type_node))
return (unsignedp ? widest_unsigned_literal_type_node return (unsignedp ? widest_unsigned_literal_type_node
: widest_integer_literal_type_node); : widest_integer_literal_type_node);
@ -3913,6 +3926,8 @@ c_common_signed_or_unsigned_type (int unsignedp, tree type)
tree tree
c_build_bitfield_integer_type (unsigned HOST_WIDE_INT width, int unsignedp) c_build_bitfield_integer_type (unsigned HOST_WIDE_INT width, int unsignedp)
{ {
int i;
/* Extended integer types of the same width as a standard type have /* Extended integer types of the same width as a standard type have
lesser rank, so those of the same width as int promote to int or lesser rank, so those of the same width as int promote to int or
unsigned int and are valid for printf formats expecting int or unsigned int and are valid for printf formats expecting int or
@ -3930,10 +3945,11 @@ c_build_bitfield_integer_type (unsigned HOST_WIDE_INT width, int unsignedp)
if (width == TYPE_PRECISION (long_long_integer_type_node)) if (width == TYPE_PRECISION (long_long_integer_type_node))
return (unsignedp ? long_long_unsigned_type_node return (unsignedp ? long_long_unsigned_type_node
: long_long_integer_type_node); : long_long_integer_type_node);
if (int128_integer_type_node for (i = 0; i < NUM_INT_N_ENTS; i ++)
&& width == TYPE_PRECISION (int128_integer_type_node)) if (int_n_enabled_p[i]
return (unsignedp ? int128_unsigned_type_node && width == int_n_data[i].bitsize)
: int128_integer_type_node); return (unsignedp ? int_n_trees[i].unsigned_type
: int_n_trees[i].signed_type);
return build_nonstandard_integer_type (width, unsignedp); return build_nonstandard_integer_type (width, unsignedp);
} }
@ -5338,6 +5354,7 @@ c_common_nodes_and_builtins (void)
tree array_domain_type; tree array_domain_type;
tree va_list_ref_type_node; tree va_list_ref_type_node;
tree va_list_arg_type_node; tree va_list_arg_type_node;
int i;
build_common_tree_nodes (flag_signed_char, flag_short_double); build_common_tree_nodes (flag_signed_char, flag_short_double);
@ -5354,13 +5371,19 @@ c_common_nodes_and_builtins (void)
record_builtin_type (RID_UNSIGNED, "unsigned int", unsigned_type_node); record_builtin_type (RID_UNSIGNED, "unsigned int", unsigned_type_node);
record_builtin_type (RID_MAX, "long unsigned int", record_builtin_type (RID_MAX, "long unsigned int",
long_unsigned_type_node); long_unsigned_type_node);
if (int128_integer_type_node != NULL_TREE)
for (i = 0; i < NUM_INT_N_ENTS; i ++)
{ {
record_builtin_type (RID_INT128, "__int128", char name[25];
int128_integer_type_node);
record_builtin_type (RID_MAX, "__int128 unsigned", sprintf (name, "__int%d", int_n_data[i].bitsize);
int128_unsigned_type_node); record_builtin_type ((enum rid)(RID_FIRST_INT_N + i), xstrdup (name),
int_n_trees[i].signed_type);
sprintf (name, "__int%d unsigned", int_n_data[i].bitsize);
record_builtin_type (RID_MAX, xstrdup (name),
int_n_trees[i].unsigned_type);
} }
if (c_dialect_cxx ()) if (c_dialect_cxx ())
record_builtin_type (RID_MAX, "unsigned long", long_unsigned_type_node); record_builtin_type (RID_MAX, "unsigned long", long_unsigned_type_node);
record_builtin_type (RID_MAX, "long long int", record_builtin_type (RID_MAX, "long long int",
@ -5396,6 +5419,8 @@ c_common_nodes_and_builtins (void)
TYPE_DECL, NULL_TREE, TYPE_DECL, NULL_TREE,
intDI_type_node)); intDI_type_node));
#if HOST_BITS_PER_WIDE_INT >= 64 #if HOST_BITS_PER_WIDE_INT >= 64
/* Note that this is different than the __int128 type that's part of
the generic __intN support. */
if (targetm.scalar_mode_supported_p (TImode)) if (targetm.scalar_mode_supported_p (TImode))
lang_hooks.decls.pushdecl (build_decl (UNKNOWN_LOCATION, lang_hooks.decls.pushdecl (build_decl (UNKNOWN_LOCATION,
TYPE_DECL, TYPE_DECL,
@ -11762,7 +11787,6 @@ keyword_begins_type_specifier (enum rid keyword)
case RID_FLOAT: case RID_FLOAT:
case RID_DOUBLE: case RID_DOUBLE:
case RID_VOID: case RID_VOID:
case RID_INT128:
case RID_UNSIGNED: case RID_UNSIGNED:
case RID_LONG: case RID_LONG:
case RID_SHORT: case RID_SHORT:
@ -11785,6 +11809,10 @@ keyword_begins_type_specifier (enum rid keyword)
case RID_ENUM: case RID_ENUM:
return true; return true;
default: default:
if (keyword >= RID_FIRST_INT_N
&& keyword < RID_FIRST_INT_N + NUM_INT_N_ENTS
&& int_n_enabled_p[keyword-RID_FIRST_INT_N])
return true;
return false; return false;
} }
} }

View File

@ -91,7 +91,6 @@ enum rid
/* C */ /* C */
RID_INT, RID_CHAR, RID_FLOAT, RID_DOUBLE, RID_VOID, RID_INT, RID_CHAR, RID_FLOAT, RID_DOUBLE, RID_VOID,
RID_INT128,
RID_ENUM, RID_STRUCT, RID_UNION, RID_IF, RID_ELSE, RID_ENUM, RID_STRUCT, RID_UNION, RID_IF, RID_ELSE,
RID_WHILE, RID_DO, RID_FOR, RID_SWITCH, RID_CASE, RID_WHILE, RID_DO, RID_FOR, RID_SWITCH, RID_CASE,
RID_DEFAULT, RID_BREAK, RID_CONTINUE, RID_RETURN, RID_GOTO, RID_DEFAULT, RID_BREAK, RID_CONTINUE, RID_RETURN, RID_GOTO,
@ -190,6 +189,23 @@ enum rid
RID_FIRST_ADDR_SPACE = RID_ADDR_SPACE_0, RID_FIRST_ADDR_SPACE = RID_ADDR_SPACE_0,
RID_LAST_ADDR_SPACE = RID_ADDR_SPACE_15, RID_LAST_ADDR_SPACE = RID_ADDR_SPACE_15,
/* __intN keywords. The _N_M here doesn't correspond to the intN
in the keyword; use the bitsize in int_n_t_data_t[M] for that.
For example, if int_n_t_data_t[0].bitsize is 13, then RID_INT_N_0
is for __int13. */
/* Note that the range to use is RID_FIRST_INT_N through
RID_FIRST_INT_N + NUM_INT_N_ENTS - 1 and c-parser.c has a list of
all RID_INT_N_* in a case statement. */
RID_INT_N_0,
RID_INT_N_1,
RID_INT_N_2,
RID_INT_N_3,
RID_FIRST_INT_N = RID_INT_N_0,
RID_LAST_INT_N = RID_INT_N_3,
RID_MAX, RID_MAX,
RID_FIRST_MODIFIER = RID_STATIC, RID_FIRST_MODIFIER = RID_STATIC,

View File

@ -771,6 +771,8 @@ cpp_iec_559_complex_value (void)
void void
c_cpp_builtins (cpp_reader *pfile) c_cpp_builtins (cpp_reader *pfile)
{ {
int i;
/* -undef turns off target-specific built-ins. */ /* -undef turns off target-specific built-ins. */
if (flag_undef) if (flag_undef)
return; return;
@ -889,6 +891,23 @@ c_cpp_builtins (cpp_reader *pfile)
builtin_define_type_max ("__PTRDIFF_MAX__", ptrdiff_type_node); builtin_define_type_max ("__PTRDIFF_MAX__", ptrdiff_type_node);
builtin_define_type_max ("__SIZE_MAX__", size_type_node); builtin_define_type_max ("__SIZE_MAX__", size_type_node);
for (i = 0; i < NUM_INT_N_ENTS; i ++)
if (int_n_enabled_p[i])
{
char buf[35+20+20];
/* These are used to configure the C++ library. */
if (!flag_iso || int_n_data[i].bitsize == POINTER_SIZE)
{
sprintf (buf, "__GLIBCXX_TYPE_INT_N_%d=__int%d", i, int_n_data[i].bitsize);
cpp_define (parse_in, buf);
sprintf (buf, "__GLIBCXX_BITSIZE_INT_N_%d=%d", i, int_n_data[i].bitsize);
cpp_define (parse_in, buf);
}
}
/* stdint.h and the testsuite need to know these. */ /* stdint.h and the testsuite need to know these. */
builtin_define_stdint_macros (); builtin_define_stdint_macros ();
@ -1169,9 +1188,14 @@ c_cpp_builtins (cpp_reader *pfile)
if (flag_openmp) if (flag_openmp)
cpp_define (pfile, "_OPENMP=201307"); cpp_define (pfile, "_OPENMP=201307");
if (int128_integer_type_node != NULL_TREE) for (i = 0; i < NUM_INT_N_ENTS; i ++)
builtin_define_type_sizeof ("__SIZEOF_INT128__", if (int_n_enabled_p[i])
int128_integer_type_node); {
char buf[15+20];
sprintf(buf, "__SIZEOF_INT%d__", int_n_data[i].bitsize);
builtin_define_type_sizeof (buf,
int_n_trees[i].signed_type);
}
builtin_define_type_sizeof ("__SIZEOF_WCHAR_T__", wchar_type_node); builtin_define_type_sizeof ("__SIZEOF_WCHAR_T__", wchar_type_node);
builtin_define_type_sizeof ("__SIZEOF_WINT_T__", wint_type_node); builtin_define_type_sizeof ("__SIZEOF_WINT_T__", wint_type_node);
builtin_define_type_sizeof ("__SIZEOF_PTRDIFF_T__", builtin_define_type_sizeof ("__SIZEOF_PTRDIFF_T__",
@ -1445,12 +1469,15 @@ type_suffix (tree type)
static const char *const suffixes[] = { "", "U", "L", "UL", "LL", "ULL" }; static const char *const suffixes[] = { "", "U", "L", "UL", "LL", "ULL" };
int unsigned_suffix; int unsigned_suffix;
int is_long; int is_long;
int tp = TYPE_PRECISION (type);
if (type == long_long_integer_type_node if (type == long_long_integer_type_node
|| type == long_long_unsigned_type_node) || type == long_long_unsigned_type_node
|| tp > TYPE_PRECISION (long_integer_type_node))
is_long = 2; is_long = 2;
else if (type == long_integer_type_node else if (type == long_integer_type_node
|| type == long_unsigned_type_node) || type == long_unsigned_type_node
|| tp > TYPE_PRECISION (integer_type_node))
is_long = 1; is_long = 1;
else if (type == integer_type_node else if (type == integer_type_node
|| type == unsigned_type_node || type == unsigned_type_node

View File

@ -920,6 +920,8 @@ pp_c_void_constant (c_pretty_printer *pp)
static void static void
pp_c_integer_constant (c_pretty_printer *pp, tree i) pp_c_integer_constant (c_pretty_printer *pp, tree i)
{ {
int idx;
/* We are going to compare the type of I to other types using /* We are going to compare the type of I to other types using
pointer comparison so we need to use its canonical type. */ pointer comparison so we need to use its canonical type. */
tree type = tree type =
@ -950,9 +952,17 @@ pp_c_integer_constant (c_pretty_printer *pp, tree i)
else if (type == long_long_integer_type_node else if (type == long_long_integer_type_node
|| type == long_long_unsigned_type_node) || type == long_long_unsigned_type_node)
pp_string (pp, "ll"); pp_string (pp, "ll");
else if (type == int128_integer_type_node else for (idx = 0; idx < NUM_INT_N_ENTS; idx ++)
|| type == int128_unsigned_type_node) if (int_n_enabled_p[idx])
pp_string (pp, "I128"); {
char buf[2+20];
if (type == int_n_trees[idx].signed_type
|| type == int_n_trees[idx].unsigned_type)
{
sprintf (buf, "I%d", int_n_data[idx].bitsize);
pp_string (pp, buf);
}
}
} }
/* Print out a CHARACTER literal. */ /* Print out a CHARACTER literal. */

View File

@ -1,3 +1,18 @@
2014-10-14 DJ Delorie <dj@redhat.com>
* c-parser.c (c_parse_init): Add RID entries for each __intN.
(c_token_starts_typename): Check all __intN, not just __int128.
(c_token_starts_declspecs): Likewise.
(c_parser_declspecs): Likewise.
(c_parser_attribute_any_word): Likewise.
(c_parser_objc_selector): Likewise.
* c-tree.h (c_typespec_keyword): cts_int128 -> cts_int_n.
(struct c_declspecs): Add int_n_idx field to record *which* __intN
is specified.
* c-decl.c (declspecs_add_type): Check for all __intN, not just
__int128.
(finish_declspecs): Likewise.
2014-10-13 Anthony Brandon <anthony.brandon@gmail.com> 2014-10-13 Anthony Brandon <anthony.brandon@gmail.com>
* c-parser.c (c_parser_all_labels): New function to replace * c-parser.c (c_parser_all_labels): New function to replace

View File

@ -9369,10 +9369,11 @@ declspecs_add_type (location_t loc, struct c_declspecs *specs,
error_at (loc, error_at (loc,
("both %<long%> and %<void%> in " ("both %<long%> and %<void%> in "
"declaration specifiers")); "declaration specifiers"));
else if (specs->typespec_word == cts_int128) else if (specs->typespec_word == cts_int_n)
error_at (loc, error_at (loc,
("both %<long%> and %<__int128%> in " ("both %<long%> and %<__int%d%> in "
"declaration specifiers")); "declaration specifiers"),
int_n_data[specs->int_n_idx].bitsize);
else if (specs->typespec_word == cts_bool) else if (specs->typespec_word == cts_bool)
error_at (loc, error_at (loc,
("both %<long%> and %<_Bool%> in " ("both %<long%> and %<_Bool%> in "
@ -9417,10 +9418,11 @@ declspecs_add_type (location_t loc, struct c_declspecs *specs,
error_at (loc, error_at (loc,
("both %<short%> and %<void%> in " ("both %<short%> and %<void%> in "
"declaration specifiers")); "declaration specifiers"));
else if (specs->typespec_word == cts_int128) else if (specs->typespec_word == cts_int_n)
error_at (loc, error_at (loc,
("both %<short%> and %<__int128%> in " ("both %<short%> and %<__int%d%> in "
"declaration specifiers")); "declaration specifiers"),
int_n_data[specs->int_n_idx].bitsize);
else if (specs->typespec_word == cts_bool) else if (specs->typespec_word == cts_bool)
error_at (loc, error_at (loc,
("both %<short%> and %<_Bool%> in " ("both %<short%> and %<_Bool%> in "
@ -9594,11 +9596,12 @@ declspecs_add_type (location_t loc, struct c_declspecs *specs,
dupe = specs->saturating_p; dupe = specs->saturating_p;
pedwarn (loc, OPT_Wpedantic, pedwarn (loc, OPT_Wpedantic,
"ISO C does not support saturating types"); "ISO C does not support saturating types");
if (specs->typespec_word == cts_int128) if (specs->typespec_word == cts_int_n)
{ {
error_at (loc, error_at (loc,
("both %<_Sat%> and %<__int128%> in " ("both %<_Sat%> and %<__int%d%> in "
"declaration specifiers")); "declaration specifiers"),
int_n_data[specs->int_n_idx].bitsize);
} }
else if (specs->typespec_word == cts_auto_type) else if (specs->typespec_word == cts_auto_type)
error_at (loc, error_at (loc,
@ -9662,7 +9665,7 @@ declspecs_add_type (location_t loc, struct c_declspecs *specs,
else else
{ {
/* "void", "_Bool", "char", "int", "float", "double", "_Decimal32", /* "void", "_Bool", "char", "int", "float", "double", "_Decimal32",
"__int128", "_Decimal64", "_Decimal128", "_Fract", "_Accum" or "__intN", "_Decimal64", "_Decimal128", "_Fract", "_Accum" or
"__auto_type". */ "__auto_type". */
if (specs->typespec_word != cts_none) if (specs->typespec_word != cts_none)
{ {
@ -9703,31 +9706,41 @@ declspecs_add_type (location_t loc, struct c_declspecs *specs,
specs->locations[cdw_typespec] = loc; specs->locations[cdw_typespec] = loc;
} }
return specs; return specs;
case RID_INT128: case RID_INT_N_0:
if (int128_integer_type_node == NULL_TREE) case RID_INT_N_1:
{ case RID_INT_N_2:
error_at (loc, "%<__int128%> is not supported for this target"); case RID_INT_N_3:
return specs; specs->int_n_idx = i - RID_INT_N_0;
} if (!in_system_header_at (input_location)
if (!in_system_header_at (input_location)) /* As a special exception, allow a type that's used
for __SIZE_TYPE__. */
&& int_n_data[specs->int_n_idx].bitsize != POINTER_SIZE)
pedwarn (loc, OPT_Wpedantic, pedwarn (loc, OPT_Wpedantic,
"ISO C does not support %<__int128%> type"); "ISO C does not support %<__int%d%> types",
int_n_data[specs->int_n_idx].bitsize);
if (specs->long_p) if (specs->long_p)
error_at (loc, error_at (loc,
("both %<__int128%> and %<long%> in " ("both %<__int%d%> and %<long%> in "
"declaration specifiers")); "declaration specifiers"),
int_n_data[specs->int_n_idx].bitsize);
else if (specs->saturating_p) else if (specs->saturating_p)
error_at (loc, error_at (loc,
("both %<_Sat%> and %<__int128%> in " ("both %<_Sat%> and %<__int%d%> in "
"declaration specifiers")); "declaration specifiers"),
int_n_data[specs->int_n_idx].bitsize);
else if (specs->short_p) else if (specs->short_p)
error_at (loc, error_at (loc,
("both %<__int128%> and %<short%> in " ("both %<__int%d%> and %<short%> in "
"declaration specifiers")); "declaration specifiers"),
int_n_data[specs->int_n_idx].bitsize);
else if (! int_n_enabled_p [specs->int_n_idx])
error_at (loc,
"%<__int%d%> is not supported on this target",
int_n_data[specs->int_n_idx].bitsize);
else else
{ {
specs->typespec_word = cts_int128; specs->typespec_word = cts_int_n;
specs->locations[cdw_typespec] = loc; specs->locations[cdw_typespec] = loc;
} }
return specs; return specs;
@ -10295,12 +10308,12 @@ finish_declspecs (struct c_declspecs *specs)
specs->type = build_complex_type (specs->type); specs->type = build_complex_type (specs->type);
} }
break; break;
case cts_int128: case cts_int_n:
gcc_assert (!specs->long_p && !specs->short_p && !specs->long_long_p); gcc_assert (!specs->long_p && !specs->short_p && !specs->long_long_p);
gcc_assert (!(specs->signed_p && specs->unsigned_p)); gcc_assert (!(specs->signed_p && specs->unsigned_p));
specs->type = (specs->unsigned_p specs->type = (specs->unsigned_p
? int128_unsigned_type_node ? int_n_trees[specs->int_n_idx].unsigned_type
: int128_integer_type_node); : int_n_trees[specs->int_n_idx].signed_type);
if (specs->complex_p) if (specs->complex_p)
{ {
pedwarn (specs->locations[cdw_complex], OPT_Wpedantic, pedwarn (specs->locations[cdw_complex], OPT_Wpedantic,

View File

@ -113,6 +113,16 @@ c_parse_init (void)
C_IS_RESERVED_WORD (id) = 1; C_IS_RESERVED_WORD (id) = 1;
ridpointers [(int) c_common_reswords[i].rid] = id; ridpointers [(int) c_common_reswords[i].rid] = id;
} }
for (i = 0; i < NUM_INT_N_ENTS; i++)
{
/* We always create the symbols but they aren't always supported. */
char name[50];
sprintf (name, "__int%d", int_n_data[i].bitsize);
id = get_identifier (xstrdup (name));
C_SET_RID_CODE (id, RID_FIRST_INT_N + i);
C_IS_RESERVED_WORD (id) = 1;
}
} }
/* The C lexer intermediates between the lexer in cpplib and c-lex.c /* The C lexer intermediates between the lexer in cpplib and c-lex.c
@ -483,7 +493,6 @@ c_token_starts_typename (c_token *token)
{ {
case RID_UNSIGNED: case RID_UNSIGNED:
case RID_LONG: case RID_LONG:
case RID_INT128:
case RID_SHORT: case RID_SHORT:
case RID_SIGNED: case RID_SIGNED:
case RID_COMPLEX: case RID_COMPLEX:
@ -511,6 +520,10 @@ c_token_starts_typename (c_token *token)
case RID_AUTO_TYPE: case RID_AUTO_TYPE:
return true; return true;
default: default:
if (token->keyword >= RID_FIRST_INT_N
&& token->keyword < RID_FIRST_INT_N + NUM_INT_N_ENTS
&& int_n_enabled_p[token->keyword - RID_FIRST_INT_N])
return true;
return false; return false;
} }
case CPP_LESS: case CPP_LESS:
@ -641,7 +654,6 @@ c_token_starts_declspecs (c_token *token)
case RID_THREAD: case RID_THREAD:
case RID_UNSIGNED: case RID_UNSIGNED:
case RID_LONG: case RID_LONG:
case RID_INT128:
case RID_SHORT: case RID_SHORT:
case RID_SIGNED: case RID_SIGNED:
case RID_COMPLEX: case RID_COMPLEX:
@ -670,6 +682,10 @@ c_token_starts_declspecs (c_token *token)
case RID_AUTO_TYPE: case RID_AUTO_TYPE:
return true; return true;
default: default:
if (token->keyword >= RID_FIRST_INT_N
&& token->keyword < RID_FIRST_INT_N + NUM_INT_N_ENTS
&& int_n_enabled_p[token->keyword - RID_FIRST_INT_N])
return true;
return false; return false;
} }
case CPP_LESS: case CPP_LESS:
@ -2158,7 +2174,7 @@ c_parser_static_assert_declaration_no_semi (c_parser *parser)
type-specifier: type-specifier:
typeof-specifier typeof-specifier
__auto_type __auto_type
__int128 __intN
_Decimal32 _Decimal32
_Decimal64 _Decimal64
_Decimal128 _Decimal128
@ -2312,7 +2328,6 @@ c_parser_declspecs (c_parser *parser, struct c_declspecs *specs,
/* Fall through. */ /* Fall through. */
case RID_UNSIGNED: case RID_UNSIGNED:
case RID_LONG: case RID_LONG:
case RID_INT128:
case RID_SHORT: case RID_SHORT:
case RID_SIGNED: case RID_SIGNED:
case RID_COMPLEX: case RID_COMPLEX:
@ -2328,6 +2343,10 @@ c_parser_declspecs (c_parser *parser, struct c_declspecs *specs,
case RID_FRACT: case RID_FRACT:
case RID_ACCUM: case RID_ACCUM:
case RID_SAT: case RID_SAT:
case RID_INT_N_0:
case RID_INT_N_1:
case RID_INT_N_2:
case RID_INT_N_3:
if (!typespec_ok) if (!typespec_ok)
goto out; goto out;
attrs_ok = true; attrs_ok = true;
@ -3738,7 +3757,6 @@ c_parser_attribute_any_word (c_parser *parser)
case RID_STATIC: case RID_STATIC:
case RID_UNSIGNED: case RID_UNSIGNED:
case RID_LONG: case RID_LONG:
case RID_INT128:
case RID_CONST: case RID_CONST:
case RID_EXTERN: case RID_EXTERN:
case RID_REGISTER: case RID_REGISTER:
@ -3768,6 +3786,10 @@ c_parser_attribute_any_word (c_parser *parser)
case RID_TRANSACTION_CANCEL: case RID_TRANSACTION_CANCEL:
case RID_ATOMIC: case RID_ATOMIC:
case RID_AUTO_TYPE: case RID_AUTO_TYPE:
case RID_INT_N_0:
case RID_INT_N_1:
case RID_INT_N_2:
case RID_INT_N_3:
ok = true; ok = true;
break; break;
default: default:
@ -8992,7 +9014,6 @@ c_parser_objc_selector (c_parser *parser)
case RID_ALIGNOF: case RID_ALIGNOF:
case RID_UNSIGNED: case RID_UNSIGNED:
case RID_LONG: case RID_LONG:
case RID_INT128:
case RID_CONST: case RID_CONST:
case RID_SHORT: case RID_SHORT:
case RID_VOLATILE: case RID_VOLATILE:
@ -9013,6 +9034,10 @@ c_parser_objc_selector (c_parser *parser)
case RID_BOOL: case RID_BOOL:
case RID_ATOMIC: case RID_ATOMIC:
case RID_AUTO_TYPE: case RID_AUTO_TYPE:
case RID_INT_N_0:
case RID_INT_N_1:
case RID_INT_N_2:
case RID_INT_N_3:
c_parser_consume_token (parser); c_parser_consume_token (parser);
return value; return value;
default: default:

View File

@ -202,7 +202,7 @@ enum c_typespec_keyword {
cts_char, cts_char,
cts_int, cts_int,
cts_float, cts_float,
cts_int128, cts_int_n,
cts_double, cts_double,
cts_dfloat32, cts_dfloat32,
cts_dfloat64, cts_dfloat64,
@ -269,6 +269,8 @@ struct c_declspecs {
specifier, in bytes, or -1 if no such specifiers with nonzero specifier, in bytes, or -1 if no such specifiers with nonzero
alignment. */ alignment. */
int align_log; int align_log;
/* For the __intN declspec, this stores the index into the int_n_* arrays. */
int int_n_idx;
/* The storage class specifier, or csc_none if none. */ /* The storage class specifier, or csc_none if none. */
enum c_storage_class storage_class; enum c_storage_class storage_class;
/* Any type specifier keyword used such as "int", not reflecting /* Any type specifier keyword used such as "int", not reflecting

View File

@ -1,3 +1,18 @@
2014-10-14 DJ Delorie <dj@redhat.com>
* typeck.c (cp_common_type): Check for all __intN types, not just
__int128.
* decl.c (grokdeclarator): Likewise.
* rtti.c (emit_support_tinfos): Check for all __intN types, not just
__int128.
* parser.c (cp_lexer_next_token_is_decl_specifier_keyword): Check
for all __intN types, not just __int128.
(cp_parser_simple_type_specifier): Likewise.
* mangle.c (integer_type_codes): Remove int128-specific codes.
* cp-tree.h (cp_decl_specifier_seq): Add int_n_idx to store which
__intN was specified.
* lex.c (init_reswords): Reserve all __intN keywords.
2014-10-14 Marc Glisse <marc.glisse@inria.fr> 2014-10-14 Marc Glisse <marc.glisse@inria.fr>
* typeck.c (cp_build_unary_op) [TRUTH_NOT_EXPR]: Accept float vectors. * typeck.c (cp_build_unary_op) [TRUTH_NOT_EXPR]: Accept float vectors.

View File

@ -4899,6 +4899,8 @@ typedef struct cp_decl_specifier_seq {
/* The storage class specified -- or sc_none if no storage class was /* The storage class specified -- or sc_none if no storage class was
explicitly specified. */ explicitly specified. */
cp_storage_class storage_class; cp_storage_class storage_class;
/* For the __intN declspec, this stores the index into the int_n_* arrays. */
int int_n_idx;
/* True iff TYPE_SPEC defines a class or enum. */ /* True iff TYPE_SPEC defines a class or enum. */
BOOL_BITFIELD type_definition_p : 1; BOOL_BITFIELD type_definition_p : 1;
/* True iff multiple types were (erroneously) specified for this /* True iff multiple types were (erroneously) specified for this
@ -4914,8 +4916,8 @@ typedef struct cp_decl_specifier_seq {
BOOL_BITFIELD any_type_specifiers_p : 1; BOOL_BITFIELD any_type_specifiers_p : 1;
/* True iff "int" was explicitly provided. */ /* True iff "int" was explicitly provided. */
BOOL_BITFIELD explicit_int_p : 1; BOOL_BITFIELD explicit_int_p : 1;
/* True iff "__int128" was explicitly provided. */ /* True iff "__intN" was explicitly provided. */
BOOL_BITFIELD explicit_int128_p : 1; BOOL_BITFIELD explicit_intN_p : 1;
/* True iff "char" was explicitly provided. */ /* True iff "char" was explicitly provided. */
BOOL_BITFIELD explicit_char_p : 1; BOOL_BITFIELD explicit_char_p : 1;
/* True iff ds_thread is set for __thread, not thread_local. */ /* True iff ds_thread is set for __thread, not thread_local. */

View File

@ -8802,7 +8802,7 @@ grokdeclarator (const cp_declarator *declarator,
{ {
tree type = NULL_TREE; tree type = NULL_TREE;
int longlong = 0; int longlong = 0;
int explicit_int128 = 0; int explicit_intN = 0;
int virtualp, explicitp, friendp, inlinep, staticp; int virtualp, explicitp, friendp, inlinep, staticp;
int explicit_int = 0; int explicit_int = 0;
int explicit_char = 0; int explicit_char = 0;
@ -8875,7 +8875,7 @@ grokdeclarator (const cp_declarator *declarator,
short_p = decl_spec_seq_has_spec_p (declspecs, ds_short); short_p = decl_spec_seq_has_spec_p (declspecs, ds_short);
long_p = decl_spec_seq_has_spec_p (declspecs, ds_long); long_p = decl_spec_seq_has_spec_p (declspecs, ds_long);
longlong = decl_spec_seq_has_spec_p (declspecs, ds_long_long); longlong = decl_spec_seq_has_spec_p (declspecs, ds_long_long);
explicit_int128 = declspecs->explicit_int128_p; explicit_intN = declspecs->explicit_intN_p;
thread_p = decl_spec_seq_has_spec_p (declspecs, ds_thread); thread_p = decl_spec_seq_has_spec_p (declspecs, ds_thread);
if (decl_context == FUNCDEF) if (decl_context == FUNCDEF)
@ -9221,16 +9221,18 @@ grokdeclarator (const cp_declarator *declarator,
ctype = NULL_TREE; ctype = NULL_TREE;
if (explicit_int128) if (explicit_intN)
{ {
if (int128_integer_type_node == NULL_TREE) if (! int_n_enabled_p[declspecs->int_n_idx])
{ {
error ("%<__int128%> is not supported by this target"); error ("%<__int%d%> is not supported by this target",
explicit_int128 = false; int_n_data[declspecs->int_n_idx].bitsize);
} explicit_intN = false;
}
else if (pedantic && ! in_system_header_at (input_location)) else if (pedantic && ! in_system_header_at (input_location))
pedwarn (input_location, OPT_Wpedantic, pedwarn (input_location, OPT_Wpedantic,
"ISO C++ does not support %<__int128%> for %qs", name); "ISO C++ does not support %<__int%d%> for %qs",
int_n_data[declspecs->int_n_idx].bitsize, name);
} }
/* Now process the modifiers that were specified /* Now process the modifiers that were specified
@ -9262,7 +9264,7 @@ grokdeclarator (const cp_declarator *declarator,
error ("%<short%> invalid for %qs", name); error ("%<short%> invalid for %qs", name);
else if ((long_p || short_p) && TREE_CODE (type) != INTEGER_TYPE) else if ((long_p || short_p) && TREE_CODE (type) != INTEGER_TYPE)
error ("%<long%> or %<short%> invalid for %qs", name); error ("%<long%> or %<short%> invalid for %qs", name);
else if ((long_p || short_p || explicit_char || explicit_int) && explicit_int128) else if ((long_p || short_p || explicit_char || explicit_int) && explicit_intN)
error ("%<long%>, %<int%>, %<short%>, or %<char%> invalid for %qs", name); error ("%<long%>, %<int%>, %<short%>, or %<char%> invalid for %qs", name);
else if ((long_p || short_p) && explicit_char) else if ((long_p || short_p) && explicit_char)
error ("%<long%> or %<short%> specified with char for %qs", name); error ("%<long%> or %<short%> specified with char for %qs", name);
@ -9278,7 +9280,7 @@ grokdeclarator (const cp_declarator *declarator,
else else
{ {
ok = 1; ok = 1;
if (!explicit_int && !defaulted_int && !explicit_char && !explicit_int128 && pedantic) if (!explicit_int && !defaulted_int && !explicit_char && !explicit_intN && pedantic)
{ {
pedwarn (input_location, OPT_Wpedantic, pedwarn (input_location, OPT_Wpedantic,
"long, short, signed or unsigned used invalidly for %qs", "long, short, signed or unsigned used invalidly for %qs",
@ -9320,8 +9322,8 @@ grokdeclarator (const cp_declarator *declarator,
&& TREE_CODE (type) == INTEGER_TYPE && TREE_CODE (type) == INTEGER_TYPE
&& !same_type_p (TYPE_MAIN_VARIANT (type), wchar_type_node))) && !same_type_p (TYPE_MAIN_VARIANT (type), wchar_type_node)))
{ {
if (explicit_int128) if (explicit_intN)
type = int128_unsigned_type_node; type = int_n_trees[declspecs->int_n_idx].unsigned_type;
else if (longlong) else if (longlong)
type = long_long_unsigned_type_node; type = long_long_unsigned_type_node;
else if (long_p) else if (long_p)
@ -9337,8 +9339,8 @@ grokdeclarator (const cp_declarator *declarator,
} }
else if (signed_p && type == char_type_node) else if (signed_p && type == char_type_node)
type = signed_char_type_node; type = signed_char_type_node;
else if (explicit_int128) else if (explicit_intN)
type = int128_integer_type_node; type = int_n_trees[declspecs->int_n_idx].signed_type;
else if (longlong) else if (longlong)
type = long_long_integer_type_node; type = long_long_integer_type_node;
else if (long_p) else if (long_p)
@ -9354,7 +9356,7 @@ grokdeclarator (const cp_declarator *declarator,
"complex double", but if any modifiers at all are specified it is "complex double", but if any modifiers at all are specified it is
the complex form of TYPE. E.g, "complex short" is the complex form of TYPE. E.g, "complex short" is
"complex short int". */ "complex short int". */
else if (defaulted_int && ! longlong && ! explicit_int128 else if (defaulted_int && ! longlong && ! explicit_intN
&& ! (long_p || short_p || signed_p || unsigned_p)) && ! (long_p || short_p || signed_p || unsigned_p))
type = complex_double_type_node; type = complex_double_type_node;
else if (type == integer_type_node) else if (type == integer_type_node)

View File

@ -193,6 +193,15 @@ init_reswords (void)
if (! (c_common_reswords[i].disable & mask)) if (! (c_common_reswords[i].disable & mask))
C_IS_RESERVED_WORD (id) = 1; C_IS_RESERVED_WORD (id) = 1;
} }
for (i = 0; i < NUM_INT_N_ENTS; i++)
{
char name[50];
sprintf (name, "__int%d", int_n_data[i].bitsize);
id = get_identifier (name);
C_SET_RID_CODE (id, RID_FIRST_INT_N + i);
C_IS_RESERVED_WORD (id) = 1;
}
} }
static void static void

View File

@ -154,8 +154,8 @@ integer_type_codes[itk_none] =
'm', /* itk_unsigned_long */ 'm', /* itk_unsigned_long */
'x', /* itk_long_long */ 'x', /* itk_long_long */
'y', /* itk_unsigned_long_long */ 'y', /* itk_unsigned_long_long */
'n', /* itk_int128 */ /* __intN types are handled separately */
'o', /* itk_unsigned_int128 */ '\0', '\0', '\0', '\0', '\0', '\0', '\0', '\0'
}; };
static int decl_is_template_id (const tree, tree* const); static int decl_is_template_id (const tree, tree* const);
@ -2215,6 +2215,7 @@ write_builtin_type (tree type)
iagain: iagain:
for (itk = 0; itk < itk_none; ++itk) for (itk = 0; itk < itk_none; ++itk)
if (integer_types[itk] != NULL_TREE if (integer_types[itk] != NULL_TREE
&& integer_type_codes[itk] != '\0'
&& type == integer_types[itk]) && type == integer_types[itk])
{ {
/* Print the corresponding single-letter code. */ /* Print the corresponding single-letter code. */

View File

@ -947,7 +947,6 @@ cp_lexer_next_token_is_decl_specifier_keyword (cp_lexer *lexer)
case RID_SHORT: case RID_SHORT:
case RID_INT: case RID_INT:
case RID_LONG: case RID_LONG:
case RID_INT128:
case RID_SIGNED: case RID_SIGNED:
case RID_UNSIGNED: case RID_UNSIGNED:
case RID_FLOAT: case RID_FLOAT:
@ -962,6 +961,10 @@ cp_lexer_next_token_is_decl_specifier_keyword (cp_lexer *lexer)
return true; return true;
default: default:
if (token->keyword >= RID_FIRST_INT_N
&& token->keyword < RID_FIRST_INT_N + NUM_INT_N_ENTS
&& int_n_enabled_p[token->keyword - RID_FIRST_INT_N])
return true;
return false; return false;
} }
} }
@ -14664,6 +14667,7 @@ cp_parser_simple_type_specifier (cp_parser* parser,
{ {
tree type = NULL_TREE; tree type = NULL_TREE;
cp_token *token; cp_token *token;
int idx;
/* Peek at the next token. */ /* Peek at the next token. */
token = cp_lexer_peek_token (parser->lexer); token = cp_lexer_peek_token (parser->lexer);
@ -14697,12 +14701,19 @@ cp_parser_simple_type_specifier (cp_parser* parser,
decl_specs->explicit_int_p = true; decl_specs->explicit_int_p = true;
type = integer_type_node; type = integer_type_node;
break; break;
case RID_INT128: case RID_INT_N_0:
if (!int128_integer_type_node) case RID_INT_N_1:
case RID_INT_N_2:
case RID_INT_N_3:
idx = token->keyword - RID_INT_N_0;
if (! int_n_enabled_p [idx])
break; break;
if (decl_specs) if (decl_specs)
decl_specs->explicit_int128_p = true; {
type = int128_integer_type_node; decl_specs->explicit_intN_p = true;
decl_specs->int_n_idx = idx;
}
type = int_n_trees [idx].signed_type;
break; break;
case RID_LONG: case RID_LONG:
if (decl_specs) if (decl_specs)

View File

@ -1520,7 +1520,6 @@ emit_support_tinfos (void)
&integer_type_node, &unsigned_type_node, &integer_type_node, &unsigned_type_node,
&long_integer_type_node, &long_unsigned_type_node, &long_integer_type_node, &long_unsigned_type_node,
&long_long_integer_type_node, &long_long_unsigned_type_node, &long_long_integer_type_node, &long_long_unsigned_type_node,
&int128_integer_type_node, &int128_unsigned_type_node,
&float_type_node, &double_type_node, &long_double_type_node, &float_type_node, &double_type_node, &long_double_type_node,
&dfloat32_type_node, &dfloat64_type_node, &dfloat128_type_node, &dfloat32_type_node, &dfloat64_type_node, &dfloat128_type_node,
&nullptr_type_node, &nullptr_type_node,
@ -1542,6 +1541,12 @@ emit_support_tinfos (void)
doing_runtime = 1; doing_runtime = 1;
for (ix = 0; fundamentals[ix]; ix++) for (ix = 0; fundamentals[ix]; ix++)
emit_support_tinfo_1 (*fundamentals[ix]); emit_support_tinfo_1 (*fundamentals[ix]);
for (ix = 0; ix < NUM_INT_N_ENTS; ix ++)
if (int_n_enabled_p[ix])
{
emit_support_tinfo_1 (int_n_trees[ix].signed_type);
emit_support_tinfo_1 (int_n_trees[ix].unsigned_type);
}
} }
/* Finish a type info decl. DECL_PTR is a pointer to an unemitted /* Finish a type info decl. DECL_PTR is a pointer to an unemitted

View File

@ -270,6 +270,7 @@ cp_common_type (tree t1, tree t2)
enum tree_code code1 = TREE_CODE (t1); enum tree_code code1 = TREE_CODE (t1);
enum tree_code code2 = TREE_CODE (t2); enum tree_code code2 = TREE_CODE (t2);
tree attributes; tree attributes;
int i;
/* In what follows, we slightly generalize the rules given in [expr] so /* In what follows, we slightly generalize the rules given in [expr] so
@ -364,16 +365,19 @@ cp_common_type (tree t1, tree t2)
: long_long_integer_type_node); : long_long_integer_type_node);
return build_type_attribute_variant (t, attributes); return build_type_attribute_variant (t, attributes);
} }
if (int128_integer_type_node != NULL_TREE for (i = 0; i < NUM_INT_N_ENTS; i ++)
&& (same_type_p (TYPE_MAIN_VARIANT (t1),
int128_integer_type_node)
|| same_type_p (TYPE_MAIN_VARIANT (t2),
int128_integer_type_node)))
{ {
tree t = ((TYPE_UNSIGNED (t1) || TYPE_UNSIGNED (t2)) if (int_n_enabled_p [i]
? int128_unsigned_type_node && (same_type_p (TYPE_MAIN_VARIANT (t1),
: int128_integer_type_node); int_n_trees[i].signed_type)
return build_type_attribute_variant (t, attributes); || same_type_p (TYPE_MAIN_VARIANT (t2),
int_n_trees[i].signed_type)))
{
tree t = ((TYPE_UNSIGNED (t1) || TYPE_UNSIGNED (t2))
? int_n_trees[i].unsigned_type
: int_n_trees[i].signed_type);
return build_type_attribute_variant (t, attributes);
}
} }
/* Go through the same procedure, but for longs. */ /* Go through the same procedure, but for longs. */

View File

@ -74,6 +74,7 @@ struct mode_data
unsigned int fbit; /* the number of fractional bits */ unsigned int fbit; /* the number of fractional bits */
bool need_bytesize_adj; /* true if this mode need dynamic size bool need_bytesize_adj; /* true if this mode need dynamic size
adjustment */ adjustment */
unsigned int int_n; /* If nonzero, then __int<INT_N> will be defined */
}; };
static struct mode_data *modes[MAX_MODE_CLASS]; static struct mode_data *modes[MAX_MODE_CLASS];
@ -84,7 +85,7 @@ static const struct mode_data blank_mode = {
0, "<unknown>", MAX_MODE_CLASS, 0, "<unknown>", MAX_MODE_CLASS,
-1U, -1U, -1U, -1U, -1U, -1U, -1U, -1U,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
"<unknown>", 0, 0, 0, 0, false "<unknown>", 0, 0, 0, 0, false, 0
}; };
static htab_t modes_by_name; static htab_t modes_by_name;
@ -632,6 +633,34 @@ reset_float_format (const char *name, const char *format,
m->format = format; m->format = format;
} }
/* __intN support. */
#define INT_N(M,PREC) \
make_int_n (#M, PREC, __FILE__, __LINE__)
static void ATTRIBUTE_UNUSED
make_int_n (const char *m, int bitsize,
const char *file, unsigned int line)
{
struct mode_data *component = find_mode (m);
if (!component)
{
error ("%s:%d: no mode \"%s\"", file, line, m);
return;
}
if (component->cl != MODE_INT
&& component->cl != MODE_PARTIAL_INT)
{
error ("%s:%d: mode \"%s\" is not class INT or PARTIAL_INT", file, line, m);
return;
}
if (component->int_n != 0)
{
error ("%s:%d: mode \"%s\" already has an intN", file, line, m);
return;
}
component->int_n = bitsize;
}
/* Partial integer modes are specified by relation to a full integer /* Partial integer modes are specified by relation to a full integer
mode. */ mode. */
#define PARTIAL_INT_MODE(M,PREC,NAME) \ #define PARTIAL_INT_MODE(M,PREC,NAME) \
@ -1010,6 +1039,7 @@ emit_insn_modes_h (void)
{ {
int c; int c;
struct mode_data *m, *first, *last; struct mode_data *m, *first, *last;
int n_int_n_ents = 0;
printf ("/* Generated automatically from machmode.def%s%s\n", printf ("/* Generated automatically from machmode.def%s%s\n",
HAVE_EXTRA_MODES ? " and " : "", HAVE_EXTRA_MODES ? " and " : "",
@ -1071,6 +1101,13 @@ enum machine_mode\n{");
printf ("#define CONST_MODE_IBIT%s\n", adj_ibit ? "" : " const"); printf ("#define CONST_MODE_IBIT%s\n", adj_ibit ? "" : " const");
printf ("#define CONST_MODE_FBIT%s\n", adj_fbit ? "" : " const"); printf ("#define CONST_MODE_FBIT%s\n", adj_fbit ? "" : " const");
emit_max_int (); emit_max_int ();
for_all_modes (c, m)
if (m->int_n)
n_int_n_ents ++;
printf ("#define NUM_INT_N_ENTS %d\n", n_int_n_ents);
puts ("\n#if GCC_VERSION >= 4001\n"); puts ("\n#if GCC_VERSION >= 4001\n");
emit_mode_size_inline (); emit_mode_size_inline ();
emit_mode_nunits_inline (); emit_mode_nunits_inline ();
@ -1520,6 +1557,53 @@ emit_mode_fbit (void)
print_closer (); print_closer ();
} }
/* Emit __intN for all modes. */
static void
emit_mode_int_n (void)
{
int c;
struct mode_data *m;
struct mode_data **mode_sort;
int n_modes = 0;
int i, j;
print_decl ("int_n_data_t", "int_n_data", "");
n_modes = 0;
for_all_modes (c, m)
if (m->int_n)
n_modes ++;
mode_sort = XALLOCAVEC (struct mode_data *, n_modes);
n_modes = 0;
for_all_modes (c, m)
if (m->int_n)
mode_sort[n_modes++] = m;
/* Yes, this is a bubblesort, but there are at most four (and
usually only 1-2) entries to sort. */
for (i = 0; i<n_modes - 1; i++)
for (j = i + 1; j < n_modes; j++)
if (mode_sort[i]->int_n > mode_sort[j]->int_n)
{
m = mode_sort[i];
mode_sort[i] = mode_sort[j];
mode_sort[j] = m;
}
for (i = 0; i < n_modes; i ++)
{
m = mode_sort[i];
printf(" {\n");
tagged_printf ("%u", m->int_n, m->name);
printf ("%smode,", m->name);
printf(" },\n");
}
print_closer ();
}
static void static void
emit_insn_modes_c (void) emit_insn_modes_c (void)
@ -1539,6 +1623,7 @@ emit_insn_modes_c (void)
emit_mode_adjustments (); emit_mode_adjustments ();
emit_mode_ibit (); emit_mode_ibit ();
emit_mode_fbit (); emit_mode_fbit ();
emit_mode_int_n ();
} }
static void static void

View File

@ -2113,6 +2113,7 @@ static tree
gimple_signed_or_unsigned_type (bool unsignedp, tree type) gimple_signed_or_unsigned_type (bool unsignedp, tree type)
{ {
tree type1; tree type1;
int i;
type1 = TYPE_MAIN_VARIANT (type); type1 = TYPE_MAIN_VARIANT (type);
if (type1 == signed_char_type_node if (type1 == signed_char_type_node
@ -2130,10 +2131,15 @@ gimple_signed_or_unsigned_type (bool unsignedp, tree type)
return unsignedp return unsignedp
? long_long_unsigned_type_node ? long_long_unsigned_type_node
: long_long_integer_type_node; : long_long_integer_type_node;
if (int128_integer_type_node && (type1 == int128_integer_type_node || type1 == int128_unsigned_type_node))
return unsignedp for (i = 0; i < NUM_INT_N_ENTS; i ++)
? int128_unsigned_type_node if (int_n_enabled_p[i]
: int128_integer_type_node; && (type1 == int_n_trees[i].unsigned_type
|| type1 == int_n_trees[i].signed_type))
return unsignedp
? int_n_trees[i].unsigned_type
: int_n_trees[i].signed_type;
#if HOST_BITS_PER_WIDE_INT >= 64 #if HOST_BITS_PER_WIDE_INT >= 64
if (type1 == intTI_type_node || type1 == unsigned_intTI_type_node) if (type1 == intTI_type_node || type1 == unsigned_intTI_type_node)
return unsignedp ? unsigned_intTI_type_node : intTI_type_node; return unsignedp ? unsigned_intTI_type_node : intTI_type_node;
@ -2246,10 +2252,14 @@ gimple_signed_or_unsigned_type (bool unsignedp, tree type)
return (unsignedp return (unsignedp
? long_long_unsigned_type_node ? long_long_unsigned_type_node
: long_long_integer_type_node); : long_long_integer_type_node);
if (int128_integer_type_node && TYPE_OK (int128_integer_type_node))
return (unsignedp for (i = 0; i < NUM_INT_N_ENTS; i ++)
? int128_unsigned_type_node if (int_n_enabled_p[i]
: int128_integer_type_node); && TYPE_MODE (type) == int_n_data[i].m
&& TYPE_PRECISION (type) == int_n_data[i].bitsize)
return unsignedp
? int_n_trees[i].unsigned_type
: int_n_trees[i].signed_type;
#if HOST_BITS_PER_WIDE_INT >= 64 #if HOST_BITS_PER_WIDE_INT >= 64
if (TYPE_OK (intTI_type_node)) if (TYPE_OK (intTI_type_node))

View File

@ -1,3 +1,9 @@
2014-10-14 DJ Delorie <dj@redhat.com>
* lto-lang.c (lto_build_c_type_nodes): Check intN types for
size-type as well.
(lto_init): Initialize all intN types, not just int128.
2014-10-06 Martin Liska <mliska@suse.cz> 2014-10-06 Martin Liska <mliska@suse.cz>
* lto.c (stream_out): ARG_UNUSED added for last argument. * lto.c (stream_out): ARG_UNUSED added for last argument.

View File

@ -1150,7 +1150,26 @@ lto_build_c_type_nodes (void)
signed_size_type_node = long_long_integer_type_node; signed_size_type_node = long_long_integer_type_node;
} }
else else
gcc_unreachable (); {
int i;
signed_size_type_node = NULL_TREE;
for (i = 0; i < NUM_INT_N_ENTS; i++)
if (int_n_enabled_p[i])
{
char name[50];
sprintf (name, "__int%d unsigned", int_n_data[i].bitsize);
if (strcmp (name, SIZE_TYPE) == 0)
{
intmax_type_node = int_n_trees[i].signed_type;
uintmax_type_node = int_n_trees[i].unsigned_type;
signed_size_type_node = int_n_trees[i].signed_type;
}
}
if (signed_size_type_node == NULL_TREE)
gcc_unreachable ();
}
wint_type_node = unsigned_type_node; wint_type_node = unsigned_type_node;
pid_type_node = integer_type_node; pid_type_node = integer_type_node;
@ -1161,6 +1180,8 @@ lto_build_c_type_nodes (void)
static bool static bool
lto_init (void) lto_init (void)
{ {
int i;
/* We need to generate LTO if running in WPA mode. */ /* We need to generate LTO if running in WPA mode. */
flag_generate_lto = (flag_wpa != NULL); flag_generate_lto = (flag_wpa != NULL);
@ -1232,8 +1253,13 @@ lto_init (void)
NAME_TYPE (complex_float_type_node, "complex float"); NAME_TYPE (complex_float_type_node, "complex float");
NAME_TYPE (complex_double_type_node, "complex double"); NAME_TYPE (complex_double_type_node, "complex double");
NAME_TYPE (complex_long_double_type_node, "complex long double"); NAME_TYPE (complex_long_double_type_node, "complex long double");
if (int128_integer_type_node) for (i = 0; i < NUM_INT_N_ENTS; i++)
NAME_TYPE (int128_integer_type_node, "__int128"); if (int_n_enabled_p[i])
{
char name[50];
sprintf (name, "__int%d", int_n_data[i].bitsize);
NAME_TYPE (int_n_trees[i].signed_type, name);
}
#undef NAME_TYPE #undef NAME_TYPE
/* Initialize LTO-specific data structures. */ /* Initialize LTO-specific data structures. */

View File

@ -192,6 +192,13 @@ INT_MODE (TI, 16);
/* No partial integer modes are defined by default. */ /* No partial integer modes are defined by default. */
/* The target normally defines any target-specific __intN types and
their modes, but __int128 for TImode is fairly common so define it
here. The type will not be created unless the target supports
TImode. */
INT_N (TI, 128);
/* Basic floating point modes. SF and DF are the only modes provided /* Basic floating point modes. SF and DF are the only modes provided
by default. The names QF, HF, XF, and TF are reserved for targets by default. The names QF, HF, XF, and TF are reserved for targets
that need 1-word, 2-word, 80-bit, or 128-bit float types respectively. that need 1-word, 2-word, 80-bit, or 128-bit float types respectively.

View File

@ -345,4 +345,16 @@ extern void init_adjust_machine_modes (void);
(SCALAR_INT_MODE_P (MODE) \ (SCALAR_INT_MODE_P (MODE) \
&& GET_MODE_PRECISION (MODE) <= HOST_BITS_PER_WIDE_INT) && GET_MODE_PRECISION (MODE) <= HOST_BITS_PER_WIDE_INT)
typedef struct {
/* These parts are initailized by genmodes output */
unsigned int bitsize;
enum machine_mode m;
/* RID_* is RID_INTN_BASE + index into this array */
} int_n_data_t;
/* This is also in tree.h. genmodes.c guarantees the're sorted from
smallest bitsize to largest bitsize. */
extern bool int_n_enabled_p[NUM_INT_N_ENTS];
extern const int_n_data_t int_n_data[NUM_INT_N_ENTS];
#endif /* not HAVE_MACHINE_MODES */ #endif /* not HAVE_MACHINE_MODES */

View File

@ -313,6 +313,7 @@ enum machine_mode
mode_for_size (unsigned int size, enum mode_class mclass, int limit) mode_for_size (unsigned int size, enum mode_class mclass, int limit)
{ {
enum machine_mode mode; enum machine_mode mode;
int i;
if (limit && size > MAX_FIXED_MODE_SIZE) if (limit && size > MAX_FIXED_MODE_SIZE)
return BLKmode; return BLKmode;
@ -323,6 +324,12 @@ mode_for_size (unsigned int size, enum mode_class mclass, int limit)
if (GET_MODE_PRECISION (mode) == size) if (GET_MODE_PRECISION (mode) == size)
return mode; return mode;
if (mclass == MODE_INT || mclass == MODE_PARTIAL_INT)
for (i = 0; i < NUM_INT_N_ENTS; i ++)
if (int_n_data[i].bitsize == size
&& int_n_enabled_p[i])
return int_n_data[i].m;
return BLKmode; return BLKmode;
} }
@ -349,16 +356,27 @@ mode_for_size_tree (const_tree size, enum mode_class mclass, int limit)
enum machine_mode enum machine_mode
smallest_mode_for_size (unsigned int size, enum mode_class mclass) smallest_mode_for_size (unsigned int size, enum mode_class mclass)
{ {
enum machine_mode mode; enum machine_mode mode = VOIDmode;
int i;
/* Get the first mode which has at least this size, in the /* Get the first mode which has at least this size, in the
specified class. */ specified class. */
for (mode = GET_CLASS_NARROWEST_MODE (mclass); mode != VOIDmode; for (mode = GET_CLASS_NARROWEST_MODE (mclass); mode != VOIDmode;
mode = GET_MODE_WIDER_MODE (mode)) mode = GET_MODE_WIDER_MODE (mode))
if (GET_MODE_PRECISION (mode) >= size) if (GET_MODE_PRECISION (mode) >= size)
return mode; break;
gcc_unreachable (); if (mclass == MODE_INT || mclass == MODE_PARTIAL_INT)
for (i = 0; i < NUM_INT_N_ENTS; i ++)
if (int_n_data[i].bitsize >= size
&& int_n_data[i].bitsize < GET_MODE_PRECISION (mode)
&& int_n_enabled_p[i])
mode = int_n_data[i].m;
if (mode == VOIDmode)
gcc_unreachable ();
return mode;
} }
/* Find an integer mode of the exact same size, or BLKmode on failure. */ /* Find an integer mode of the exact same size, or BLKmode on failure. */
@ -2550,7 +2568,24 @@ initialize_sizetypes (void)
else if (strcmp (SIZETYPE, "short unsigned int") == 0) else if (strcmp (SIZETYPE, "short unsigned int") == 0)
precision = SHORT_TYPE_SIZE; precision = SHORT_TYPE_SIZE;
else else
gcc_unreachable (); {
int i;
precision = -1;
for (i = 0; i < NUM_INT_N_ENTS; i++)
if (int_n_enabled_p[i])
{
char name[50];
sprintf (name, "__int%d unsigned", int_n_data[i].bitsize);
if (strcmp (name, SIZETYPE) == 0)
{
precision = int_n_data[i].bitsize;
}
}
if (precision == -1)
gcc_unreachable ();
}
bprecision bprecision
= MIN (precision + BITS_PER_UNIT_LOG + 1, MAX_FIXED_MODE_SIZE); = MIN (precision + BITS_PER_UNIT_LOG + 1, MAX_FIXED_MODE_SIZE);

View File

@ -1,3 +1,7 @@
2014-10-14 DJ Delorie <dj@redhat.com>
* g++.dg/abi/mangle64.C: New.
2014-10-14 Marc Glisse <marc.glisse@inria.fr> 2014-10-14 Marc Glisse <marc.glisse@inria.fr>
* g++.dg/ext/vector9.C: Test ! with float vectors. * g++.dg/ext/vector9.C: Test ! with float vectors.

View File

@ -0,0 +1,13 @@
// { dg-do compile { target msp430*-*-* } }
// { dg-options "-std=gnu++11" }
// { dg-skip-if "" { msp430*-*-* } { "-mcpu=msp430" } { "" } }
__int20 x;
__int20 foo (__int20 a, unsigned __int20 b)
{
return a + b;
}
// { dg-final { scan-assembler "\n_?_Z3foou5int20u6uint20\[: \t\n\]" } }

View File

@ -1901,6 +1901,21 @@ finalize (bool no_backend)
lang_hooks.finish (); lang_hooks.finish ();
} }
static bool
standard_type_bitsize (int bitsize)
{
/* As a special exception, we always want __int128 enabled if possible. */
if (bitsize == 128)
return false;
if (bitsize == CHAR_TYPE_SIZE
|| bitsize == SHORT_TYPE_SIZE
|| bitsize == INT_TYPE_SIZE
|| bitsize == LONG_TYPE_SIZE
|| bitsize == LONG_LONG_TYPE_SIZE)
return true;
return false;
}
/* Initialize the compiler, and compile the input file. */ /* Initialize the compiler, and compile the input file. */
static void static void
do_compile (void) do_compile (void)
@ -1916,6 +1931,8 @@ do_compile (void)
/* Don't do any more if an error has already occurred. */ /* Don't do any more if an error has already occurred. */
if (!seen_error ()) if (!seen_error ())
{ {
int i;
timevar_start (TV_PHASE_SETUP); timevar_start (TV_PHASE_SETUP);
/* This must be run always, because it is needed to compute the FP /* This must be run always, because it is needed to compute the FP
@ -1924,6 +1941,16 @@ do_compile (void)
init_adjust_machine_modes (); init_adjust_machine_modes ();
init_derived_machine_modes (); init_derived_machine_modes ();
/* This must happen after the backend has a chance to process
command line options, but before the parsers are
initialized. */
for (i = 0; i < NUM_INT_N_ENTS; i ++)
if (targetm.scalar_mode_supported_p (int_n_data[i].m)
&& ! standard_type_bitsize (int_n_data[i].bitsize))
int_n_enabled_p[i] = true;
else
int_n_enabled_p[i] = false;
/* Set up the back-end if requested. */ /* Set up the back-end if requested. */
if (!no_backend) if (!no_backend)
backend_init (); backend_init ();

View File

@ -570,8 +570,16 @@ enum integer_type_kind {
itk_unsigned_long, itk_unsigned_long,
itk_long_long, itk_long_long,
itk_unsigned_long_long, itk_unsigned_long_long,
itk_int128,
itk_unsigned_int128, itk_intN_0,
itk_unsigned_intN_0,
itk_intN_1,
itk_unsigned_intN_1,
itk_intN_2,
itk_unsigned_intN_2,
itk_intN_3,
itk_unsigned_intN_3,
itk_none itk_none
}; };

View File

@ -236,6 +236,9 @@ static void attribute_hash_list (const_tree, inchash::hash &);
tree global_trees[TI_MAX]; tree global_trees[TI_MAX];
tree integer_types[itk_none]; tree integer_types[itk_none];
bool int_n_enabled_p[NUM_INT_N_ENTS];
struct int_n_trees_t int_n_trees [NUM_INT_N_ENTS];
unsigned char tree_contains_struct[MAX_TREE_CODES][64]; unsigned char tree_contains_struct[MAX_TREE_CODES][64];
/* Number of operands for each OpenMP clause. */ /* Number of operands for each OpenMP clause. */
@ -9445,6 +9448,8 @@ make_vector_type (tree innertype, int nunits, enum machine_mode mode)
static tree static tree
make_or_reuse_type (unsigned size, int unsignedp) make_or_reuse_type (unsigned size, int unsignedp)
{ {
int i;
if (size == INT_TYPE_SIZE) if (size == INT_TYPE_SIZE)
return unsignedp ? unsigned_type_node : integer_type_node; return unsignedp ? unsigned_type_node : integer_type_node;
if (size == CHAR_TYPE_SIZE) if (size == CHAR_TYPE_SIZE)
@ -9456,9 +9461,12 @@ make_or_reuse_type (unsigned size, int unsignedp)
if (size == LONG_LONG_TYPE_SIZE) if (size == LONG_LONG_TYPE_SIZE)
return (unsignedp ? long_long_unsigned_type_node return (unsignedp ? long_long_unsigned_type_node
: long_long_integer_type_node); : long_long_integer_type_node);
if (size == 128 && int128_integer_type_node)
return (unsignedp ? int128_unsigned_type_node for (i = 0; i < NUM_INT_N_ENTS; i ++)
: int128_integer_type_node); if (size == int_n_data[i].bitsize
&& int_n_enabled_p[i])
return (unsignedp ? int_n_trees[i].unsigned_type
: int_n_trees[i].signed_type);
if (unsignedp) if (unsignedp)
return make_unsigned_type (size); return make_unsigned_type (size);
@ -9574,6 +9582,8 @@ build_atomic_base (tree type, unsigned int align)
void void
build_common_tree_nodes (bool signed_char, bool short_double) build_common_tree_nodes (bool signed_char, bool short_double)
{ {
int i;
error_mark_node = make_node (ERROR_MARK); error_mark_node = make_node (ERROR_MARK);
TREE_TYPE (error_mark_node) = error_mark_node; TREE_TYPE (error_mark_node) = error_mark_node;
@ -9601,17 +9611,20 @@ build_common_tree_nodes (bool signed_char, bool short_double)
long_unsigned_type_node = make_unsigned_type (LONG_TYPE_SIZE); long_unsigned_type_node = make_unsigned_type (LONG_TYPE_SIZE);
long_long_integer_type_node = make_signed_type (LONG_LONG_TYPE_SIZE); long_long_integer_type_node = make_signed_type (LONG_LONG_TYPE_SIZE);
long_long_unsigned_type_node = make_unsigned_type (LONG_LONG_TYPE_SIZE); long_long_unsigned_type_node = make_unsigned_type (LONG_LONG_TYPE_SIZE);
#if HOST_BITS_PER_WIDE_INT >= 64
/* TODO: This isn't correct, but as logic depends at the moment on for (i = 0; i < NUM_INT_N_ENTS; i ++)
host's instead of target's wide-integer. {
If there is a target not supporting TImode, but has an 128-bit int_n_trees[i].signed_type = make_signed_type (int_n_data[i].bitsize);
integer-scalar register, this target check needs to be adjusted. */ int_n_trees[i].unsigned_type = make_unsigned_type (int_n_data[i].bitsize);
if (targetm.scalar_mode_supported_p (TImode)) TYPE_SIZE (int_n_trees[i].signed_type) = bitsize_int (int_n_data[i].bitsize);
{ TYPE_SIZE (int_n_trees[i].unsigned_type) = bitsize_int (int_n_data[i].bitsize);
int128_integer_type_node = make_signed_type (128);
int128_unsigned_type_node = make_unsigned_type (128); if (int_n_data[i].bitsize > LONG_LONG_TYPE_SIZE)
} {
#endif integer_types[itk_intN_0 + i * 2] = int_n_trees[i].signed_type;
integer_types[itk_unsigned_intN_0 + i * 2] = int_n_trees[i].unsigned_type;
}
}
/* Define a boolean type. This type only represents boolean values but /* Define a boolean type. This type only represents boolean values but
may be larger than char depending on the value of BOOL_TYPE_SIZE. */ may be larger than char depending on the value of BOOL_TYPE_SIZE. */
@ -9630,7 +9643,24 @@ build_common_tree_nodes (bool signed_char, bool short_double)
else if (strcmp (SIZE_TYPE, "short unsigned int") == 0) else if (strcmp (SIZE_TYPE, "short unsigned int") == 0)
size_type_node = short_unsigned_type_node; size_type_node = short_unsigned_type_node;
else else
gcc_unreachable (); {
int i;
size_type_node = NULL_TREE;
for (i = 0; i < NUM_INT_N_ENTS; i++)
if (int_n_enabled_p[i])
{
char name[50];
sprintf (name, "__int%d unsigned", int_n_data[i].bitsize);
if (strcmp (name, SIZE_TYPE) == 0)
{
size_type_node = int_n_trees[i].unsigned_type;
}
}
if (size_type_node == NULL_TREE)
gcc_unreachable ();
}
/* Fill in the rest of the sized types. Reuse existing type nodes /* Fill in the rest of the sized types. Reuse existing type nodes
when possible. */ when possible. */

View File

@ -3426,8 +3426,6 @@ tree_operand_check_code (const_tree __t, enum tree_code __code, int __i,
#define long_unsigned_type_node integer_types[itk_unsigned_long] #define long_unsigned_type_node integer_types[itk_unsigned_long]
#define long_long_integer_type_node integer_types[itk_long_long] #define long_long_integer_type_node integer_types[itk_long_long]
#define long_long_unsigned_type_node integer_types[itk_unsigned_long_long] #define long_long_unsigned_type_node integer_types[itk_unsigned_long_long]
#define int128_integer_type_node integer_types[itk_int128]
#define int128_unsigned_type_node integer_types[itk_unsigned_int128]
/* True if NODE is an erroneous expression. */ /* True if NODE is an erroneous expression. */
@ -4800,6 +4798,17 @@ extern tree get_inner_reference (tree, HOST_WIDE_INT *, HOST_WIDE_INT *,
EXP, an ARRAY_REF or an ARRAY_RANGE_REF. */ EXP, an ARRAY_REF or an ARRAY_RANGE_REF. */
extern tree array_ref_low_bound (tree); extern tree array_ref_low_bound (tree);
struct GTY(()) int_n_trees_t {
/* These parts are initialized at runtime */
tree signed_type;
tree unsigned_type;
};
/* This is also in machmode.h */
extern bool int_n_enabled_p[NUM_INT_N_ENTS];
extern GTY(()) struct int_n_trees_t int_n_trees[NUM_INT_N_ENTS];
/* Like bit_position, but return as an integer. It must be representable in /* Like bit_position, but return as an integer. It must be representable in
that way (since it could be a signed value, we don't have the that way (since it could be a signed value, we don't have the
option of returning -1 like int_size_in_byte can. */ option of returning -1 like int_size_in_byte can. */

View File

@ -1,3 +1,12 @@
2014-10-14 DJ Delorie <dj@redhat.com>
* src/c++11/limits.cc: Add support for __intN types.
* include/std/type_traits: Likewise.
* include/std/limits: Likewise.
* include/c_std/cstdlib: Likewise.
* include/bits/cpp_type_traits.h: Likewise.
* include/c_global/cstdlib: Likewise.
2014-10-14 Jonathan Wakely <jwakely@redhat.com> 2014-10-14 Jonathan Wakely <jwakely@redhat.com>
* testsuite/20_util/align/1.cc: Add dg-require-stdint. * testsuite/20_util/align/1.cc: Add dg-require-stdint.

View File

@ -141,7 +141,8 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
// Thirteen specializations (yes there are eleven standard integer // Thirteen specializations (yes there are eleven standard integer
// types; <em>long long</em> and <em>unsigned long long</em> are // types; <em>long long</em> and <em>unsigned long long</em> are
// supported as extensions) // supported as extensions). Up to four target-specific __int<N>
// types are supported as well.
template<> template<>
struct __is_integer<bool> struct __is_integer<bool>
{ {
@ -251,6 +252,35 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
typedef __true_type __type; typedef __true_type __type;
}; };
#define __INT_N(TYPE) \
template<> \
struct __is_integer<TYPE> \
{ \
enum { __value = 1 }; \
typedef __true_type __type; \
}; \
template<> \
struct __is_integer<unsigned TYPE> \
{ \
enum { __value = 1 }; \
typedef __true_type __type; \
};
#ifdef __GLIBCXX_TYPE_INT_N_0
__INT_N(__GLIBCXX_TYPE_INT_N_0)
#endif
#ifdef __GLIBCXX_TYPE_INT_N_1
__INT_N(__GLIBCXX_TYPE_INT_N_1)
#endif
#ifdef __GLIBCXX_TYPE_INT_N_2
__INT_N(__GLIBCXX_TYPE_INT_N_2)
#endif
#ifdef __GLIBCXX_TYPE_INT_N_3
__INT_N(__GLIBCXX_TYPE_INT_N_3)
#endif
#undef __INT_N
// //
// Floating point types // Floating point types
// //

View File

@ -174,10 +174,23 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
abs(long long __x) { return __builtin_llabs (__x); } abs(long long __x) { return __builtin_llabs (__x); }
#endif #endif
#if !defined(__STRICT_ANSI__) && defined(_GLIBCXX_USE_INT128) #if defined(__GLIBCXX_TYPE_INT_N_0)
inline __int128 inline __GLIBCXX_TYPE_INT_N_0
abs(__int128 __x) { return __x >= 0 ? __x : -__x; } abs(__GLIBCXX_TYPE_INT_N_0 __x) { return __x >= 0 ? __x : -__x; }
#endif #endif
#if defined(__GLIBCXX_TYPE_INT_N_1)
inline __GLIBCXX_TYPE_INT_N_1
abs(__GLIBCXX_TYPE_INT_N_1 __x) { return __x >= 0 ? __x : -__x; }
#endif
#if defined(__GLIBCXX_TYPE_INT_N_2)
inline __GLIBCXX_TYPE_INT_N_2
abs(__GLIBCXX_TYPE_INT_N_2 __x) { return __x >= 0 ? __x : -__x; }
#endif
#if defined(__GLIBCXX_TYPE_INT_N_3)
inline __GLIBCXX_TYPE_INT_N_3
abs(__GLIBCXX_TYPE_INT_N_3 __x) { return __x >= 0 ? __x : -__x; }
#endif
_GLIBCXX_END_NAMESPACE_VERSION _GLIBCXX_END_NAMESPACE_VERSION
} // namespace } // namespace

View File

@ -169,9 +169,21 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
abs(long long __x) { return __builtin_llabs (__x); } abs(long long __x) { return __builtin_llabs (__x); }
#endif #endif
#if !defined(__STRICT_ANSI__) && defined(_GLIBCXX_USE_INT128) #if defined(__GLIBCXX_TYPE_INT_N_0)
inline __int128 inline __GLIBCXX_TYPE_INT_N_0
abs(__int128 __x) { return __x >= 0 ? __x : -__x; } abs(__GLIBCXX_TYPE_INT_N_0 __x) { return __x >= 0 ? __x : -__x; }
#endif
#if defined(__GLIBCXX_TYPE_INT_N_1)
inline __GLIBCXX_TYPE_INT_N_1
abs(__GLIBCXX_TYPE_INT_N_1 __x) { return __x >= 0 ? __x : -__x; }
#endif
#if defined(__GLIBCXX_TYPE_INT_N_2)
inline __GLIBCXX_TYPE_INT_N_2
abs(__GLIBCXX_TYPE_INT_N_2 __x) { return __x >= 0 ? __x : -__x; }
#endif
#if defined(__GLIBCXX_TYPE_INT_N_3)
inline __GLIBCXX_TYPE_INT_N_3
abs(__GLIBCXX_TYPE_INT_N_3 __x) { return __x >= 0 ? __x : -__x; }
#endif #endif
inline ldiv_t inline ldiv_t

View File

@ -125,21 +125,32 @@
// You should not need to define any macros below this point. // You should not need to define any macros below this point.
#define __glibcxx_signed(T) ((T)(-1) < 0) #define __glibcxx_signed_b(T,B) ((T)(-1) < 0)
#define __glibcxx_min(T) \ #define __glibcxx_min_b(T,B) \
(__glibcxx_signed (T) ? -__glibcxx_max (T) - 1 : (T)0) (__glibcxx_signed_b (T,B) ? -__glibcxx_max_b (T,B) - 1 : (T)0)
#define __glibcxx_max(T) \ #define __glibcxx_max_b(T,B) \
(__glibcxx_signed (T) ? \ (__glibcxx_signed_b (T,B) ? \
(((((T)1 << (__glibcxx_digits (T) - 1)) - 1) << 1) + 1) : ~(T)0) (((((T)1 << (__glibcxx_digits_b (T,B) - 1)) - 1) << 1) + 1) : ~(T)0)
#define __glibcxx_digits(T) \ #define __glibcxx_digits_b(T,B) \
(sizeof(T) * __CHAR_BIT__ - __glibcxx_signed (T)) (B - __glibcxx_signed_b (T,B))
// The fraction 643/2136 approximates log10(2) to 7 significant digits. // The fraction 643/2136 approximates log10(2) to 7 significant digits.
#define __glibcxx_digits10_b(T,B) \
(__glibcxx_digits_b (T,B) * 643L / 2136)
#define __glibcxx_signed(T) \
__glibcxx_signed_b (T, sizeof(T) * __CHAR_BIT__)
#define __glibcxx_min(T) \
__glibcxx_min_b (T, sizeof(T) * __CHAR_BIT__)
#define __glibcxx_max(T) \
__glibcxx_max_b (T, sizeof(T) * __CHAR_BIT__)
#define __glibcxx_digits(T) \
__glibcxx_digits_b (T, sizeof(T) * __CHAR_BIT__)
#define __glibcxx_digits10(T) \ #define __glibcxx_digits10(T) \
(__glibcxx_digits (T) * 643L / 2136) __glibcxx_digits10_b (T, sizeof(T) * __CHAR_BIT__)
#define __glibcxx_max_digits10(T) \ #define __glibcxx_max_digits10(T) \
(2 + (T) * 643L / 2136) (2 + (T) * 643L / 2136)
@ -1399,153 +1410,181 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
= round_toward_zero; = round_toward_zero;
}; };
#if !defined(__STRICT_ANSI__) && defined(_GLIBCXX_USE_INT128) #if !defined(__STRICT_ANSI__)
/// numeric_limits<__int128> specialization.
template<>
struct numeric_limits<__int128>
{
static _GLIBCXX_USE_CONSTEXPR bool is_specialized = true;
static _GLIBCXX_CONSTEXPR __int128 #define __INT_N(TYPE, BITSIZE, EXT, UEXT) \
min() _GLIBCXX_USE_NOEXCEPT { return __glibcxx_min (__int128); } template<> \
struct numeric_limits<TYPE> \
static _GLIBCXX_CONSTEXPR __int128 { \
max() _GLIBCXX_USE_NOEXCEPT { return __glibcxx_max (__int128); } static _GLIBCXX_USE_CONSTEXPR bool is_specialized = true; \
\
#if __cplusplus >= 201103L static _GLIBCXX_CONSTEXPR TYPE \
static constexpr __int128 min() _GLIBCXX_USE_NOEXCEPT { return __glibcxx_min_b (TYPE, BITSIZE); } \
lowest() noexcept { return min(); } \
#endif static _GLIBCXX_CONSTEXPR TYPE \
max() _GLIBCXX_USE_NOEXCEPT { return __glibcxx_max_b (TYPE, BITSIZE);; } \
static _GLIBCXX_USE_CONSTEXPR int digits \
= __glibcxx_digits (__int128); static _GLIBCXX_USE_CONSTEXPR int digits \
static _GLIBCXX_USE_CONSTEXPR int digits10 = BITSIZE - 1; \
= __glibcxx_digits10 (__int128); static _GLIBCXX_USE_CONSTEXPR int digits10 \
#if __cplusplus >= 201103L = (BITSIZE - 1) * 643L / 2136; \
static constexpr int max_digits10 = 0; \
#endif static _GLIBCXX_USE_CONSTEXPR bool is_signed = true; \
static _GLIBCXX_USE_CONSTEXPR bool is_signed = true; static _GLIBCXX_USE_CONSTEXPR bool is_integer = true; \
static _GLIBCXX_USE_CONSTEXPR bool is_integer = true; static _GLIBCXX_USE_CONSTEXPR bool is_exact = true; \
static _GLIBCXX_USE_CONSTEXPR bool is_exact = true; static _GLIBCXX_USE_CONSTEXPR int radix = 2; \
static _GLIBCXX_USE_CONSTEXPR int radix = 2; \
static _GLIBCXX_CONSTEXPR TYPE \
static _GLIBCXX_CONSTEXPR __int128 epsilon() _GLIBCXX_USE_NOEXCEPT { return 0; } \
epsilon() _GLIBCXX_USE_NOEXCEPT { return 0; } \
static _GLIBCXX_CONSTEXPR TYPE \
static _GLIBCXX_CONSTEXPR __int128 round_error() _GLIBCXX_USE_NOEXCEPT { return 0; } \
round_error() _GLIBCXX_USE_NOEXCEPT { return 0; } \
EXT \
static _GLIBCXX_USE_CONSTEXPR int min_exponent = 0; \
static _GLIBCXX_USE_CONSTEXPR int min_exponent10 = 0; static _GLIBCXX_USE_CONSTEXPR int min_exponent = 0; \
static _GLIBCXX_USE_CONSTEXPR int max_exponent = 0; static _GLIBCXX_USE_CONSTEXPR int min_exponent10 = 0; \
static _GLIBCXX_USE_CONSTEXPR int max_exponent10 = 0; static _GLIBCXX_USE_CONSTEXPR int max_exponent = 0; \
static _GLIBCXX_USE_CONSTEXPR int max_exponent10 = 0; \
static _GLIBCXX_USE_CONSTEXPR bool has_infinity = false; \
static _GLIBCXX_USE_CONSTEXPR bool has_quiet_NaN = false; static _GLIBCXX_USE_CONSTEXPR bool has_infinity = false; \
static _GLIBCXX_USE_CONSTEXPR bool has_signaling_NaN = false; static _GLIBCXX_USE_CONSTEXPR bool has_quiet_NaN = false; \
static _GLIBCXX_USE_CONSTEXPR float_denorm_style has_denorm static _GLIBCXX_USE_CONSTEXPR bool has_signaling_NaN = false; \
= denorm_absent; static _GLIBCXX_USE_CONSTEXPR float_denorm_style has_denorm \
static _GLIBCXX_USE_CONSTEXPR bool has_denorm_loss = false; = denorm_absent; \
static _GLIBCXX_USE_CONSTEXPR bool has_denorm_loss = false; \
static _GLIBCXX_CONSTEXPR __int128 \
infinity() _GLIBCXX_USE_NOEXCEPT static _GLIBCXX_CONSTEXPR TYPE \
{ return static_cast<__int128>(0); } infinity() _GLIBCXX_USE_NOEXCEPT \
{ return static_cast<TYPE>(0); } \
static _GLIBCXX_CONSTEXPR __int128 \
quiet_NaN() _GLIBCXX_USE_NOEXCEPT static _GLIBCXX_CONSTEXPR TYPE \
{ return static_cast<__int128>(0); } quiet_NaN() _GLIBCXX_USE_NOEXCEPT \
{ return static_cast<TYPE>(0); } \
static _GLIBCXX_CONSTEXPR __int128 \
signaling_NaN() _GLIBCXX_USE_NOEXCEPT static _GLIBCXX_CONSTEXPR TYPE \
{ return static_cast<__int128>(0); } signaling_NaN() _GLIBCXX_USE_NOEXCEPT \
{ return static_cast<TYPE>(0); } \
static _GLIBCXX_CONSTEXPR __int128 \
denorm_min() _GLIBCXX_USE_NOEXCEPT static _GLIBCXX_CONSTEXPR TYPE \
{ return static_cast<__int128>(0); } denorm_min() _GLIBCXX_USE_NOEXCEPT \
{ return static_cast<TYPE>(0); } \
static _GLIBCXX_USE_CONSTEXPR bool is_iec559 = false; \
static _GLIBCXX_USE_CONSTEXPR bool is_bounded = true; static _GLIBCXX_USE_CONSTEXPR bool is_iec559 = false; \
static _GLIBCXX_USE_CONSTEXPR bool is_modulo = false; static _GLIBCXX_USE_CONSTEXPR bool is_bounded = true; \
static _GLIBCXX_USE_CONSTEXPR bool is_modulo = false; \
static _GLIBCXX_USE_CONSTEXPR bool traps \
= __glibcxx_integral_traps; static _GLIBCXX_USE_CONSTEXPR bool traps \
static _GLIBCXX_USE_CONSTEXPR bool tinyness_before = false; = __glibcxx_integral_traps; \
static _GLIBCXX_USE_CONSTEXPR float_round_style round_style static _GLIBCXX_USE_CONSTEXPR bool tinyness_before = false; \
= round_toward_zero; static _GLIBCXX_USE_CONSTEXPR float_round_style round_style \
= round_toward_zero; \
}; \
\
template<> \
struct numeric_limits<unsigned TYPE> \
{ \
static _GLIBCXX_USE_CONSTEXPR bool is_specialized = true; \
\
static _GLIBCXX_CONSTEXPR unsigned TYPE \
min() _GLIBCXX_USE_NOEXCEPT { return 0; } \
\
static _GLIBCXX_CONSTEXPR unsigned TYPE \
max() _GLIBCXX_USE_NOEXCEPT { return __glibcxx_max_b (TYPE, BITSIZE); } \
\
UEXT \
\
static _GLIBCXX_USE_CONSTEXPR int digits \
= BITSIZE; \
static _GLIBCXX_USE_CONSTEXPR int digits10 \
= BITSIZE * 643L / 2136; \
static _GLIBCXX_USE_CONSTEXPR bool is_signed = false; \
static _GLIBCXX_USE_CONSTEXPR bool is_integer = true; \
static _GLIBCXX_USE_CONSTEXPR bool is_exact = true; \
static _GLIBCXX_USE_CONSTEXPR int radix = 2; \
\
static _GLIBCXX_CONSTEXPR unsigned TYPE \
epsilon() _GLIBCXX_USE_NOEXCEPT { return 0; } \
\
static _GLIBCXX_CONSTEXPR unsigned TYPE \
round_error() _GLIBCXX_USE_NOEXCEPT { return 0; } \
\
static _GLIBCXX_USE_CONSTEXPR int min_exponent = 0; \
static _GLIBCXX_USE_CONSTEXPR int min_exponent10 = 0; \
static _GLIBCXX_USE_CONSTEXPR int max_exponent = 0; \
static _GLIBCXX_USE_CONSTEXPR int max_exponent10 = 0; \
\
static _GLIBCXX_USE_CONSTEXPR bool has_infinity = false; \
static _GLIBCXX_USE_CONSTEXPR bool has_quiet_NaN = false; \
static _GLIBCXX_USE_CONSTEXPR bool has_signaling_NaN = false; \
static _GLIBCXX_USE_CONSTEXPR float_denorm_style has_denorm \
= denorm_absent; \
static _GLIBCXX_USE_CONSTEXPR bool has_denorm_loss = false; \
\
static _GLIBCXX_CONSTEXPR unsigned TYPE \
infinity() _GLIBCXX_USE_NOEXCEPT \
{ return static_cast<unsigned TYPE>(0); } \
\
static _GLIBCXX_CONSTEXPR unsigned TYPE \
quiet_NaN() _GLIBCXX_USE_NOEXCEPT \
{ return static_cast<unsigned TYPE>(0); } \
\
static _GLIBCXX_CONSTEXPR unsigned TYPE \
signaling_NaN() _GLIBCXX_USE_NOEXCEPT \
{ return static_cast<unsigned TYPE>(0); } \
\
static _GLIBCXX_CONSTEXPR unsigned TYPE \
denorm_min() _GLIBCXX_USE_NOEXCEPT \
{ return static_cast<unsigned TYPE>(0); } \
\
static _GLIBCXX_USE_CONSTEXPR bool is_iec559 = false; \
static _GLIBCXX_USE_CONSTEXPR bool is_bounded = true; \
static _GLIBCXX_USE_CONSTEXPR bool is_modulo = true; \
\
static _GLIBCXX_USE_CONSTEXPR bool traps = __glibcxx_integral_traps; \
static _GLIBCXX_USE_CONSTEXPR bool tinyness_before = false; \
static _GLIBCXX_USE_CONSTEXPR float_round_style round_style \
= round_toward_zero; \
}; };
/// numeric_limits<unsigned __int128> specialization.
template<>
struct numeric_limits<unsigned __int128>
{
static _GLIBCXX_USE_CONSTEXPR bool is_specialized = true;
static _GLIBCXX_CONSTEXPR unsigned __int128
min() _GLIBCXX_USE_NOEXCEPT { return 0; }
static _GLIBCXX_CONSTEXPR unsigned __int128
max() _GLIBCXX_USE_NOEXCEPT { return __glibcxx_max (unsigned __int128); }
#if __cplusplus >= 201103L #if __cplusplus >= 201103L
static constexpr unsigned __int128
lowest() noexcept { return min(); }
#endif
static _GLIBCXX_USE_CONSTEXPR int digits #define __INT_N_201103(TYPE) \
= __glibcxx_digits (unsigned __int128); static constexpr TYPE \
static _GLIBCXX_USE_CONSTEXPR int digits10 lowest() noexcept { return min(); } \
= __glibcxx_digits10 (unsigned __int128);
#if __cplusplus >= 201103L
static constexpr int max_digits10 = 0; static constexpr int max_digits10 = 0;
#define __INT_N_U201103(TYPE) \
static constexpr unsigned TYPE \
lowest() noexcept { return min(); } \
static constexpr int max_digits10 = 0;
#else
#define __INT_N_201103(TYPE)
#define __INT_N_U201103(TYPE)
#endif #endif
static _GLIBCXX_USE_CONSTEXPR bool is_signed = false;
static _GLIBCXX_USE_CONSTEXPR bool is_integer = true;
static _GLIBCXX_USE_CONSTEXPR bool is_exact = true;
static _GLIBCXX_USE_CONSTEXPR int radix = 2;
static _GLIBCXX_CONSTEXPR unsigned __int128 #ifdef __GLIBCXX_TYPE_INT_N_0
epsilon() _GLIBCXX_USE_NOEXCEPT { return 0; } __INT_N(__GLIBCXX_TYPE_INT_N_0, __GLIBCXX_BITSIZE_INT_N_0,
__INT_N_201103 (__GLIBCXX_TYPE_INT_N_0), __INT_N_U201103 (__GLIBCXX_TYPE_INT_N_0))
#endif
#ifdef __GLIBCXX_TYPE_INT_N_1
__INT_N (__GLIBCXX_TYPE_INT_N_1, __GLIBCXX_BITSIZE_INT_N_1,
__INT_N_201103 (__GLIBCXX_TYPE_INT_N_1), __INT_N_U201103 (__GLIBCXX_TYPE_INT_N_1))
#endif
#ifdef __GLIBCXX_TYPE_INT_N_2
__INT_N (__GLIBCXX_TYPE_INT_N_2, __GLIBCXX_BITSIZE_INT_N_2,
__INT_N_201103 (__GLIBCXX_TYPE_INT_N_2), __INT_N_U201103 (__GLIBCXX_TYPE_INT_N_2))
#endif
#ifdef __GLIBCXX_TYPE_INT_N_3
__INT_N (__GLIBCXX_TYPE_INT_N_3, __GLIBCXX_BITSIZE_INT_N_3,
__INT_N_201103 (__GLIBCXX_TYPE_INT_N_3), __INT_N_U201103 (__GLIBCXX_TYPE_INT_N_3))
#endif
static _GLIBCXX_CONSTEXPR unsigned __int128 #undef __INT_N
round_error() _GLIBCXX_USE_NOEXCEPT { return 0; } #undef __INT_N_201103
#undef __INT_N_U201103
static _GLIBCXX_USE_CONSTEXPR int min_exponent = 0;
static _GLIBCXX_USE_CONSTEXPR int min_exponent10 = 0;
static _GLIBCXX_USE_CONSTEXPR int max_exponent = 0;
static _GLIBCXX_USE_CONSTEXPR int max_exponent10 = 0;
static _GLIBCXX_USE_CONSTEXPR bool has_infinity = false;
static _GLIBCXX_USE_CONSTEXPR bool has_quiet_NaN = false;
static _GLIBCXX_USE_CONSTEXPR bool has_signaling_NaN = false;
static _GLIBCXX_USE_CONSTEXPR float_denorm_style has_denorm
= denorm_absent;
static _GLIBCXX_USE_CONSTEXPR bool has_denorm_loss = false;
static _GLIBCXX_CONSTEXPR unsigned __int128
infinity() _GLIBCXX_USE_NOEXCEPT
{ return static_cast<unsigned __int128>(0); }
static _GLIBCXX_CONSTEXPR unsigned __int128
quiet_NaN() _GLIBCXX_USE_NOEXCEPT
{ return static_cast<unsigned __int128>(0); }
static _GLIBCXX_CONSTEXPR unsigned __int128
signaling_NaN() _GLIBCXX_USE_NOEXCEPT
{ return static_cast<unsigned __int128>(0); }
static _GLIBCXX_CONSTEXPR unsigned __int128
denorm_min() _GLIBCXX_USE_NOEXCEPT
{ return static_cast<unsigned __int128>(0); }
static _GLIBCXX_USE_CONSTEXPR bool is_iec559 = false;
static _GLIBCXX_USE_CONSTEXPR bool is_bounded = true;
static _GLIBCXX_USE_CONSTEXPR bool is_modulo = true;
static _GLIBCXX_USE_CONSTEXPR bool traps = __glibcxx_integral_traps;
static _GLIBCXX_USE_CONSTEXPR bool tinyness_before = false;
static _GLIBCXX_USE_CONSTEXPR float_round_style round_style
= round_toward_zero;
};
#endif #endif
/// numeric_limits<float> specialization. /// numeric_limits<float> specialization.

View File

@ -242,13 +242,42 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
struct __is_integral_helper<unsigned long long> struct __is_integral_helper<unsigned long long>
: public true_type { }; : public true_type { };
#if !defined(__STRICT_ANSI__) && defined(_GLIBCXX_USE_INT128) // Conditionalizing on __STRICT_ANSI__ here will break any port that
// uses one of these types for size_t.
#if defined(__GLIBCXX_TYPE_INT_N_0)
template<> template<>
struct __is_integral_helper<__int128> struct __is_integral_helper<__GLIBCXX_TYPE_INT_N_0>
: public true_type { }; : public true_type { };
template<> template<>
struct __is_integral_helper<unsigned __int128> struct __is_integral_helper<unsigned __GLIBCXX_TYPE_INT_N_0>
: public true_type { };
#endif
#if defined(__GLIBCXX_TYPE_INT_N_1)
template<>
struct __is_integral_helper<__GLIBCXX_TYPE_INT_N_1>
: public true_type { };
template<>
struct __is_integral_helper<unsigned __GLIBCXX_TYPE_INT_N_1>
: public true_type { };
#endif
#if defined(__GLIBCXX_TYPE_INT_N_2)
template<>
struct __is_integral_helper<__GLIBCXX_TYPE_INT_N_2>
: public true_type { };
template<>
struct __is_integral_helper<unsigned __GLIBCXX_TYPE_INT_N_2>
: public true_type { };
#endif
#if defined(__GLIBCXX_TYPE_INT_N_3)
template<>
struct __is_integral_helper<__GLIBCXX_TYPE_INT_N_3>
: public true_type { };
template<>
struct __is_integral_helper<unsigned __GLIBCXX_TYPE_INT_N_3>
: public true_type { }; : public true_type { };
#endif #endif
@ -1661,10 +1690,25 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
{ }; { };
#endif #endif
#if !defined(__STRICT_ANSI__) && defined(_GLIBCXX_USE_INT128) #if defined(__GLIBCXX_TYPE_INT_N_0)
template<> template<>
struct __make_unsigned<__int128> struct __make_unsigned<__GLIBCXX_TYPE_INT_N_0>
{ typedef unsigned __int128 __type; }; { typedef unsigned __GLIBCXX_TYPE_INT_N_0 __type; };
#endif
#if defined(__GLIBCXX_TYPE_INT_N_1)
template<>
struct __make_unsigned<__GLIBCXX_TYPE_INT_N_1>
{ typedef unsigned __GLIBCXX_TYPE_INT_N_1 __type; };
#endif
#if defined(__GLIBCXX_TYPE_INT_N_2)
template<>
struct __make_unsigned<__GLIBCXX_TYPE_INT_N_2>
{ typedef unsigned __GLIBCXX_TYPE_INT_N_2 __type; };
#endif
#if defined(__GLIBCXX_TYPE_INT_N_3)
template<>
struct __make_unsigned<__GLIBCXX_TYPE_INT_N_3>
{ typedef unsigned __GLIBCXX_TYPE_INT_N_3 __type; };
#endif #endif
// Select between integral and enum: not possible to be both. // Select between integral and enum: not possible to be both.
@ -1758,10 +1802,25 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
{ }; { };
#endif #endif
#if !defined(__STRICT_ANSI__) && defined(_GLIBCXX_USE_INT128) #if defined(__GLIBCXX_TYPE_INT_N_0)
template<> template<>
struct __make_signed<unsigned __int128> struct __make_signed<unsigned __GLIBCXX_TYPE_INT_N_0>
{ typedef __int128 __type; }; { typedef __GLIBCXX_TYPE_INT_N_0 __type; };
#endif
#if defined(__GLIBCXX_TYPE_INT_N_1)
template<>
struct __make_signed<unsigned __GLIBCXX_TYPE_INT_N_1>
{ typedef __GLIBCXX_TYPE_INT_N_1 __type; };
#endif
#if defined(__GLIBCXX_TYPE_INT_N_2)
template<>
struct __make_signed<unsigned __GLIBCXX_TYPE_INT_N_2>
{ typedef __GLIBCXX_TYPE_INT_N_2 __type; };
#endif
#if defined(__GLIBCXX_TYPE_INT_N_3)
template<>
struct __make_signed<unsigned __GLIBCXX_TYPE_INT_N_3>
{ typedef __GLIBCXX_TYPE_INT_N_3 __type; };
#endif #endif
// Select between integral and enum: not possible to be both. // Select between integral and enum: not possible to be both.

View File

@ -388,54 +388,66 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION
const bool numeric_limits<unsigned long long>::tinyness_before; const bool numeric_limits<unsigned long long>::tinyness_before;
const float_round_style numeric_limits<unsigned long long>::round_style; const float_round_style numeric_limits<unsigned long long>::round_style;
#if !defined(__STRICT_ANSI__) && defined(_GLIBCXX_USE_INT128) #define INT_N(__INT_N_TYPE) \
const bool numeric_limits<__int128>::is_specialized; const bool numeric_limits<__INT_N_TYPE>::is_specialized; \
const int numeric_limits<__int128>::digits; const int numeric_limits<__INT_N_TYPE>::digits; \
const int numeric_limits<__int128>::digits10; const int numeric_limits<__INT_N_TYPE>::digits10; \
const int numeric_limits<__int128>::max_digits10; const int numeric_limits<__INT_N_TYPE>::max_digits10; \
const bool numeric_limits<__int128>::is_signed; const bool numeric_limits<__INT_N_TYPE>::is_signed; \
const bool numeric_limits<__int128>::is_integer; const bool numeric_limits<__INT_N_TYPE>::is_integer; \
const bool numeric_limits<__int128>::is_exact; const bool numeric_limits<__INT_N_TYPE>::is_exact; \
const int numeric_limits<__int128>::radix; const int numeric_limits<__INT_N_TYPE>::radix; \
const int numeric_limits<__int128>::min_exponent; const int numeric_limits<__INT_N_TYPE>::min_exponent; \
const int numeric_limits<__int128>::min_exponent10; const int numeric_limits<__INT_N_TYPE>::min_exponent10; \
const int numeric_limits<__int128>::max_exponent; const int numeric_limits<__INT_N_TYPE>::max_exponent; \
const int numeric_limits<__int128>::max_exponent10; const int numeric_limits<__INT_N_TYPE>::max_exponent10; \
const bool numeric_limits<__int128>::has_infinity; const bool numeric_limits<__INT_N_TYPE>::has_infinity; \
const bool numeric_limits<__int128>::has_quiet_NaN; const bool numeric_limits<__INT_N_TYPE>::has_quiet_NaN; \
const bool numeric_limits<__int128>::has_signaling_NaN; const bool numeric_limits<__INT_N_TYPE>::has_signaling_NaN; \
const float_denorm_style numeric_limits<__int128>::has_denorm; const float_denorm_style numeric_limits<__INT_N_TYPE>::has_denorm; \
const bool numeric_limits<__int128>::has_denorm_loss; const bool numeric_limits<__INT_N_TYPE>::has_denorm_loss; \
const bool numeric_limits<__int128>::is_iec559; const bool numeric_limits<__INT_N_TYPE>::is_iec559; \
const bool numeric_limits<__int128>::is_bounded; const bool numeric_limits<__INT_N_TYPE>::is_bounded; \
const bool numeric_limits<__int128>::is_modulo; const bool numeric_limits<__INT_N_TYPE>::is_modulo; \
const bool numeric_limits<__int128>::traps; const bool numeric_limits<__INT_N_TYPE>::traps; \
const bool numeric_limits<__int128>::tinyness_before; const bool numeric_limits<__INT_N_TYPE>::tinyness_before; \
const float_round_style numeric_limits<__int128>::round_style; const float_round_style numeric_limits<__INT_N_TYPE>::round_style; \
\
const bool numeric_limits<unsigned __INT_N_TYPE>::is_specialized; \
const int numeric_limits<unsigned __INT_N_TYPE>::digits; \
const int numeric_limits<unsigned __INT_N_TYPE>::digits10; \
const int numeric_limits<unsigned __INT_N_TYPE>::max_digits10; \
const bool numeric_limits<unsigned __INT_N_TYPE>::is_signed; \
const bool numeric_limits<unsigned __INT_N_TYPE>::is_integer; \
const bool numeric_limits<unsigned __INT_N_TYPE>::is_exact; \
const int numeric_limits<unsigned __INT_N_TYPE>::radix; \
const int numeric_limits<unsigned __INT_N_TYPE>::min_exponent; \
const int numeric_limits<unsigned __INT_N_TYPE>::min_exponent10; \
const int numeric_limits<unsigned __INT_N_TYPE>::max_exponent; \
const int numeric_limits<unsigned __INT_N_TYPE>::max_exponent10; \
const bool numeric_limits<unsigned __INT_N_TYPE>::has_infinity; \
const bool numeric_limits<unsigned __INT_N_TYPE>::has_quiet_NaN; \
const bool numeric_limits<unsigned __INT_N_TYPE>::has_signaling_NaN; \
const float_denorm_style numeric_limits<unsigned __INT_N_TYPE>::has_denorm; \
const bool numeric_limits<unsigned __INT_N_TYPE>::has_denorm_loss; \
const bool numeric_limits<unsigned __INT_N_TYPE>::is_iec559; \
const bool numeric_limits<unsigned __INT_N_TYPE>::is_bounded; \
const bool numeric_limits<unsigned __INT_N_TYPE>::is_modulo; \
const bool numeric_limits<unsigned __INT_N_TYPE>::traps; \
const bool numeric_limits<unsigned __INT_N_TYPE>::tinyness_before; \
const float_round_style numeric_limits<unsigned __INT_N_TYPE>::round_style;
const bool numeric_limits<unsigned __int128>::is_specialized; #ifdef __GLIBCXX_TYPE_INT_N_0
const int numeric_limits<unsigned __int128>::digits; INT_N (__GLIBCXX_TYPE_INT_N_0)
const int numeric_limits<unsigned __int128>::digits10; #endif
const int numeric_limits<unsigned __int128>::max_digits10; #ifdef __GLIBCXX_TYPE_INT_N_1
const bool numeric_limits<unsigned __int128>::is_signed; INT_N (__GLIBCXX_TYPE_INT_N_1)
const bool numeric_limits<unsigned __int128>::is_integer; #endif
const bool numeric_limits<unsigned __int128>::is_exact; #ifdef __GLIBCXX_TYPE_INT_N_2
const int numeric_limits<unsigned __int128>::radix; INT_N (__GLIBCXX_TYPE_INT_N_2)
const int numeric_limits<unsigned __int128>::min_exponent; #endif
const int numeric_limits<unsigned __int128>::min_exponent10; #ifdef __GLIBCXX_TYPE_INT_N_3
const int numeric_limits<unsigned __int128>::max_exponent; INT_N (__GLIBCXX_TYPE_INT_N_3)
const int numeric_limits<unsigned __int128>::max_exponent10;
const bool numeric_limits<unsigned __int128>::has_infinity;
const bool numeric_limits<unsigned __int128>::has_quiet_NaN;
const bool numeric_limits<unsigned __int128>::has_signaling_NaN;
const float_denorm_style numeric_limits<unsigned __int128>::has_denorm;
const bool numeric_limits<unsigned __int128>::has_denorm_loss;
const bool numeric_limits<unsigned __int128>::is_iec559;
const bool numeric_limits<unsigned __int128>::is_bounded;
const bool numeric_limits<unsigned __int128>::is_modulo;
const bool numeric_limits<unsigned __int128>::traps;
const bool numeric_limits<unsigned __int128>::tinyness_before;
const float_round_style numeric_limits<unsigned __int128>::round_style;
#endif #endif
// float // float