X-Git-Url: http://git.sourceforge.jp/view?a=blobdiff_plain;f=gcc%2Ftree.c;h=03c54cc1cb17b0a785f8b07c80cbdf475d37a010;hb=f2bb0caab3f1442550fc59770df22b1b770a55b1;hp=912d77fd41043431e77ff351ad838bb11db94369;hpb=b9c94ed7ac6512c7551a007128fed6f3caf21ed1;p=pf3gnuchains%2Fgcc-fork.git diff --git a/gcc/tree.c b/gcc/tree.c index 912d77fd410..03c54cc1cb1 100644 --- a/gcc/tree.c +++ b/gcc/tree.c @@ -343,6 +343,8 @@ init_ttree (void) tree_contains_struct[CONST_DECL][TS_CONST_DECL] = 1; tree_contains_struct[TYPE_DECL][TS_TYPE_DECL] = 1; tree_contains_struct[FUNCTION_DECL][TS_FUNCTION_DECL] = 1; + tree_contains_struct[IMPORTED_DECL][TS_DECL_MINIMAL] = 1; + tree_contains_struct[IMPORTED_DECL][TS_DECL_COMMON] = 1; lang_hooks.init_ts (); } @@ -2492,6 +2494,11 @@ contains_placeholder_p (const_tree exp) || CONTAINS_PLACEHOLDER_P (TREE_OPERAND (exp, 1)) || CONTAINS_PLACEHOLDER_P (TREE_OPERAND (exp, 2))); + case SAVE_EXPR: + /* The save_expr function never wraps anything containing + a PLACEHOLDER_EXPR. */ + return 0; + default: break; } @@ -3282,8 +3289,13 @@ build2_stat (enum tree_code code, tree tt, tree arg0, tree arg1 MEM_STAT_DECL) gcc_assert (TREE_CODE_LENGTH (code) == 2); if ((code == MINUS_EXPR || code == PLUS_EXPR || code == MULT_EXPR) - && arg0 && arg1 && tt && POINTER_TYPE_P (tt)) - gcc_assert (TREE_CODE (arg0) == INTEGER_CST && TREE_CODE (arg1) == INTEGER_CST); + && arg0 && arg1 && tt && POINTER_TYPE_P (tt) + /* When sizetype precision doesn't match that of pointers + we need to be able to build explicit extensions or truncations + of the offset argument. */ + && TYPE_PRECISION (sizetype) == TYPE_PRECISION (tt)) + gcc_assert (TREE_CODE (arg0) == INTEGER_CST + && TREE_CODE (arg1) == INTEGER_CST); if (code == POINTER_PLUS_EXPR && arg0 && arg1 && tt) gcc_assert (POINTER_TYPE_P (tt) && POINTER_TYPE_P (TREE_TYPE (arg0)) @@ -3577,6 +3589,16 @@ set_expr_locus (tree node, source_location *loc) else EXPR_CHECK (node)->exp.locus = *loc; } + +/* Like SET_EXPR_LOCATION, but make sure the tree can have a location. + + LOC is the location to use in tree T. */ + +void protected_set_expr_location (tree t, location_t loc) +{ + if (t && CAN_HAVE_LOCATION_P (t)) + SET_EXPR_LOCATION (t, loc); +} /* Return a declaration like DDECL except that its DECL_ATTRIBUTES is ATTRIBUTE. */ @@ -3687,10 +3709,10 @@ build_type_attribute_qual_variant (tree ttype, tree attribute, int quals) return build_qualified_type (ttype, quals); } + ttype = build_qualified_type (ttype, TYPE_UNQUALIFIED); ntype = build_distinct_type_copy (ttype); TYPE_ATTRIBUTES (ntype) = attribute; - set_type_quals (ntype, TYPE_UNQUALIFIED); hashcode = iterative_hash_object (code, hashcode); if (TREE_TYPE (ntype)) @@ -3729,12 +3751,11 @@ build_type_attribute_qual_variant (tree ttype, tree attribute, int quals) /* If the target-dependent attributes make NTYPE different from its canonical type, we will need to use structural equality - checks for this qualified type. */ - ttype = build_qualified_type (ttype, TYPE_UNQUALIFIED); + checks for this type. */ if (TYPE_STRUCTURAL_EQUALITY_P (ttype) || !targetm.comp_type_attributes (ntype, ttype)) SET_TYPE_STRUCTURAL_EQUALITY (ntype); - else + else if (TYPE_CANONICAL (ntype) == ntype) TYPE_CANONICAL (ntype) = TYPE_CANONICAL (ttype); ttype = build_qualified_type (ntype, quals); @@ -4568,7 +4589,9 @@ type_hash_eq (const void *va, const void *vb) || !attribute_list_equal (TYPE_ATTRIBUTES (a->type), TYPE_ATTRIBUTES (b->type)) || TYPE_ALIGN (a->type) != TYPE_ALIGN (b->type) - || TYPE_MODE (a->type) != TYPE_MODE (b->type)) + || TYPE_MODE (a->type) != TYPE_MODE (b->type) + || (TREE_CODE (a->type) != COMPLEX_TYPE + && TYPE_NAME (a->type) != TYPE_NAME (b->type))) return 0; switch (TREE_CODE (a->type)) @@ -5017,6 +5040,33 @@ tree_int_cst_sgn (const_tree t) return 1; } +/* Return the minimum number of bits needed to represent VALUE in a + signed or unsigned type, UNSIGNEDP says which. */ + +unsigned int +tree_int_cst_min_precision (tree value, bool unsignedp) +{ + int log; + + /* If the value is negative, compute its negative minus 1. The latter + adjustment is because the absolute value of the largest negative value + is one larger than the largest positive value. This is equivalent to + a bit-wise negation, so use that operation instead. */ + + if (tree_int_cst_sgn (value) < 0) + value = fold_build1 (BIT_NOT_EXPR, TREE_TYPE (value), value); + + /* Return the number of bits needed, taking into account the fact + that we need one more bit for a signed than unsigned type. */ + + if (integer_zerop (value)) + log = 0; + else + log = tree_floor_log2 (value); + + return log + 1 + !unsignedp; +} + /* Compare two constructor-element-type constants. Return 1 if the lists are known to be equal; otherwise return 0. */ @@ -5472,7 +5522,7 @@ build_pointer_type_for_mode (tree to_type, enum machine_mode mode, t = make_node (POINTER_TYPE); TREE_TYPE (t) = to_type; - TYPE_MODE (t) = mode; + SET_TYPE_MODE (t, mode); TYPE_REF_CAN_ALIAS_ALL (t) = can_alias_all; TYPE_NEXT_PTR_TO (t) = TYPE_POINTER_TO (to_type); TYPE_POINTER_TO (to_type) = t; @@ -5536,7 +5586,7 @@ build_reference_type_for_mode (tree to_type, enum machine_mode mode, t = make_node (REFERENCE_TYPE); TREE_TYPE (t) = to_type; - TYPE_MODE (t) = mode; + SET_TYPE_MODE (t, mode); TYPE_REF_CAN_ALIAS_ALL (t) = can_alias_all; TYPE_NEXT_REF_TO (t) = TYPE_REFERENCE_TO (to_type); TYPE_REFERENCE_TO (to_type) = t; @@ -5605,7 +5655,7 @@ build_index_type (tree maxval) TYPE_PRECISION (itype) = TYPE_PRECISION (sizetype); TYPE_MIN_VALUE (itype) = size_zero_node; TYPE_MAX_VALUE (itype) = fold_convert (sizetype, maxval); - TYPE_MODE (itype) = TYPE_MODE (sizetype); + SET_TYPE_MODE (itype, TYPE_MODE (sizetype)); TYPE_SIZE (itype) = TYPE_SIZE (sizetype); TYPE_SIZE_UNIT (itype) = TYPE_SIZE_UNIT (sizetype); TYPE_ALIGN (itype) = TYPE_ALIGN (sizetype); @@ -5661,7 +5711,7 @@ build_range_type (tree type, tree lowval, tree highval) TYPE_MAX_VALUE (itype) = highval ? fold_convert (type, highval) : NULL; TYPE_PRECISION (itype) = TYPE_PRECISION (type); - TYPE_MODE (itype) = TYPE_MODE (type); + SET_TYPE_MODE (itype, TYPE_MODE (type)); TYPE_SIZE (itype) = TYPE_SIZE (type); TYPE_SIZE_UNIT (itype) = TYPE_SIZE_UNIT (type); TYPE_ALIGN (itype) = TYPE_ALIGN (type); @@ -5878,6 +5928,91 @@ build_function_type (tree value_type, tree arg_types) return t; } +/* Build variant of function type ORIG_TYPE skipping ARGS_TO_SKIP. */ + +tree +build_function_type_skip_args (tree orig_type, bitmap args_to_skip) +{ + tree new_type = NULL; + tree args, new_args = NULL, t; + tree new_reversed; + int i = 0; + + for (args = TYPE_ARG_TYPES (orig_type); args && args != void_list_node; + args = TREE_CHAIN (args), i++) + if (!bitmap_bit_p (args_to_skip, i)) + new_args = tree_cons (NULL_TREE, TREE_VALUE (args), new_args); + + new_reversed = nreverse (new_args); + if (args) + { + if (new_reversed) + TREE_CHAIN (new_args) = void_list_node; + else + new_reversed = void_list_node; + } + gcc_assert (new_reversed); + + /* Use copy_node to preserve as much as possible from original type + (debug info, attribute lists etc.) + Exception is METHOD_TYPEs must have THIS argument. + When we are asked to remove it, we need to build new FUNCTION_TYPE + instead. */ + if (TREE_CODE (orig_type) != METHOD_TYPE + || !bitmap_bit_p (args_to_skip, 0)) + { + new_type = copy_node (orig_type); + TYPE_ARG_TYPES (new_type) = new_reversed; + } + else + { + new_type + = build_distinct_type_copy (build_function_type (TREE_TYPE (orig_type), + new_reversed)); + TYPE_CONTEXT (new_type) = TYPE_CONTEXT (orig_type); + } + + /* This is a new type, not a copy of an old type. Need to reassociate + variants. We can handle everything except the main variant lazily. */ + t = TYPE_MAIN_VARIANT (orig_type); + if (orig_type != t) + { + TYPE_MAIN_VARIANT (new_type) = t; + TYPE_NEXT_VARIANT (new_type) = TYPE_NEXT_VARIANT (t); + TYPE_NEXT_VARIANT (t) = new_type; + } + else + { + TYPE_MAIN_VARIANT (new_type) = new_type; + TYPE_NEXT_VARIANT (new_type) = NULL; + } + return new_type; +} + +/* Build variant of function type ORIG_TYPE skipping ARGS_TO_SKIP. + + Arguments from DECL_ARGUMENTS list can't be removed now, since they are + linked by TREE_CHAIN directly. It is caller responsibility to eliminate + them when they are being duplicated (i.e. copy_arguments_for_versioning). */ + +tree +build_function_decl_skip_args (tree orig_decl, bitmap args_to_skip) +{ + tree new_decl = copy_node (orig_decl); + tree new_type; + + new_type = TREE_TYPE (orig_decl); + if (prototype_p (new_type)) + new_type = build_function_type_skip_args (new_type, args_to_skip); + TREE_TYPE (new_decl) = new_type; + + /* For declarations setting DECL_VINDEX (i.e. methods) + we expect first argument to be THIS pointer. */ + if (bitmap_bit_p (args_to_skip, 0)) + DECL_VINDEX (new_decl) = NULL_TREE; + return new_decl; +} + /* Build a function type. The RETURN_TYPE is the type returned by the function. If VAARGS is set, no void_type_node is appended to the the list. ARGP muse be alway be terminated be a NULL_TREE. */ @@ -5893,9 +6028,9 @@ build_function_type_list_1 (bool vaargs, tree return_type, va_list argp) if (vaargs) { - last = args; - if (args != NULL_TREE) - args = nreverse (args); + last = args; + if (args != NULL_TREE) + args = nreverse (args); gcc_assert (args != NULL_TREE && last != void_list_node); } else if (args == NULL_TREE) @@ -6065,6 +6200,10 @@ build_complex_type (tree component_type) tree t; hashval_t hashcode; + gcc_assert (INTEGRAL_TYPE_P (component_type) + || SCALAR_FLOAT_TYPE_P (component_type) + || FIXED_POINT_TYPE_P (component_type)); + /* Make a node of the sort we want. */ t = make_node (COMPLEX_TYPE); @@ -6303,11 +6442,28 @@ get_narrower (tree op, int *unsignedp_ptr) int int_fits_type_p (const_tree c, const_tree type) { - tree type_low_bound = TYPE_MIN_VALUE (type); - tree type_high_bound = TYPE_MAX_VALUE (type); - bool ok_for_low_bound, ok_for_high_bound; - unsigned HOST_WIDE_INT low; - HOST_WIDE_INT high; + tree type_low_bound, type_high_bound; + bool ok_for_low_bound, ok_for_high_bound, unsc; + double_int dc, dd; + + dc = tree_to_double_int (c); + unsc = TYPE_UNSIGNED (TREE_TYPE (c)); + + if (TREE_CODE (TREE_TYPE (c)) == INTEGER_TYPE + && TYPE_IS_SIZETYPE (TREE_TYPE (c)) + && unsc) + /* So c is an unsigned integer whose type is sizetype and type is not. + sizetype'd integers are sign extended even though they are + unsigned. If the integer value fits in the lower end word of c, + and if the higher end word has all its bits set to 1, that + means the higher end bits are set to 1 only for sign extension. + So let's convert c into an equivalent zero extended unsigned + integer. */ + dc = double_int_zext (dc, TYPE_PRECISION (TREE_TYPE (c))); + +retry: + type_low_bound = TYPE_MIN_VALUE (type); + type_high_bound = TYPE_MAX_VALUE (type); /* If at least one bound of the type is a constant integer, we can check ourselves and maybe make a decision. If no such decision is possible, but @@ -6319,10 +6475,25 @@ int_fits_type_p (const_tree c, const_tree type) for "unknown if constant fits", 0 for "constant known *not* to fit" and 1 for "constant known to fit". */ - /* Check if C >= type_low_bound. */ + /* Check if c >= type_low_bound. */ if (type_low_bound && TREE_CODE (type_low_bound) == INTEGER_CST) { - if (tree_int_cst_lt (c, type_low_bound)) + dd = tree_to_double_int (type_low_bound); + if (TREE_CODE (type) == INTEGER_TYPE + && TYPE_IS_SIZETYPE (type) + && TYPE_UNSIGNED (type)) + dd = double_int_zext (dd, TYPE_PRECISION (type)); + if (unsc != TYPE_UNSIGNED (TREE_TYPE (type_low_bound))) + { + int c_neg = (!unsc && double_int_negative_p (dc)); + int t_neg = (unsc && double_int_negative_p (dd)); + + if (c_neg && !t_neg) + return 0; + if ((c_neg || !t_neg) && double_int_ucmp (dc, dd) < 0) + return 0; + } + else if (double_int_cmp (dc, dd, unsc) < 0) return 0; ok_for_low_bound = true; } @@ -6332,7 +6503,22 @@ int_fits_type_p (const_tree c, const_tree type) /* Check if c <= type_high_bound. */ if (type_high_bound && TREE_CODE (type_high_bound) == INTEGER_CST) { - if (tree_int_cst_lt (type_high_bound, c)) + dd = tree_to_double_int (type_high_bound); + if (TREE_CODE (type) == INTEGER_TYPE + && TYPE_IS_SIZETYPE (type) + && TYPE_UNSIGNED (type)) + dd = double_int_zext (dd, TYPE_PRECISION (type)); + if (unsc != TYPE_UNSIGNED (TREE_TYPE (type_high_bound))) + { + int c_neg = (!unsc && double_int_negative_p (dc)); + int t_neg = (unsc && double_int_negative_p (dd)); + + if (t_neg && !c_neg) + return 0; + if ((t_neg || !c_neg) && double_int_ucmp (dc, dd) > 0) + return 0; + } + else if (double_int_cmp (dc, dd, unsc) > 0) return 0; ok_for_high_bound = true; } @@ -6346,7 +6532,7 @@ int_fits_type_p (const_tree c, const_tree type) /* Perform some generic filtering which may allow making a decision even if the bounds are not constant. First, negative integers never fit in unsigned types, */ - if (TYPE_UNSIGNED (type) && tree_int_cst_sgn (c) < 0) + if (TYPE_UNSIGNED (type) && !unsc && double_int_negative_p (dc)) return 0; /* Second, narrower types always fit in wider ones. */ @@ -6354,10 +6540,18 @@ int_fits_type_p (const_tree c, const_tree type) return 1; /* Third, unsigned integers with top bit set never fit signed types. */ - if (! TYPE_UNSIGNED (type) - && TYPE_UNSIGNED (TREE_TYPE (c)) - && tree_int_cst_msb (c)) - return 0; + if (! TYPE_UNSIGNED (type) && unsc) + { + int prec = GET_MODE_BITSIZE (TYPE_MODE (TREE_TYPE (c))) - 1; + if (prec < HOST_BITS_PER_WIDE_INT) + { + if (((((unsigned HOST_WIDE_INT) 1) << prec) & dc.low) != 0) + return 0; + } + else if (((((unsigned HOST_WIDE_INT) 1) + << (prec - HOST_BITS_PER_WIDE_INT)) & dc.high) != 0) + return 0; + } /* If we haven't been able to decide at this point, there nothing more we can check ourselves here. Look at the base type if we have one and it @@ -6365,12 +6559,13 @@ int_fits_type_p (const_tree c, const_tree type) if (TREE_CODE (type) == INTEGER_TYPE && TREE_TYPE (type) != 0 && TYPE_PRECISION (type) == TYPE_PRECISION (TREE_TYPE (type))) - return int_fits_type_p (c, TREE_TYPE (type)); + { + type = TREE_TYPE (type); + goto retry; + } /* Or to fit_double_type, if nothing else. */ - low = TREE_INT_CST_LOW (c); - high = TREE_INT_CST_HIGH (c); - return !fit_double_type (low, high, &low, &high, type); + return !fit_double_type (dc.low, dc.high, &dc.low, &dc.high, type); } /* Stores bounds of an integer TYPE in MIN and MAX. If TYPE has non-constant @@ -6660,9 +6855,8 @@ get_callee_fndecl (const_tree call) && TREE_CODE (TREE_OPERAND (addr, 0)) == FUNCTION_DECL) return TREE_OPERAND (addr, 0); - /* We couldn't figure out what was being called. Maybe the front - end has some idea. */ - return lang_hooks.lang_get_callee_fndecl (call); + /* We couldn't figure out what was being called. */ + return NULL_TREE; } /* Print debugging information about tree nodes generated during the compile, @@ -6765,7 +6959,7 @@ get_file_function_name (const char *type) /* If we already have a name we know to be unique, just use that. */ if (first_global_object_name) - p = first_global_object_name; + p = q = ASTRDUP (first_global_object_name); /* If the target is handling the constructors/destructors, they will be local to this file and the name is only necessary for debugging purposes. */ @@ -6782,7 +6976,6 @@ get_file_function_name (const char *type) else p = file; p = q = ASTRDUP (p); - clean_symbol_name (q); } else { @@ -6801,7 +6994,6 @@ get_file_function_name (const char *type) len = strlen (file); q = (char *) alloca (9 * 2 + len + 1); memcpy (q, file, len + 1); - clean_symbol_name (q); sprintf (q + len, "_%08X_%08X", crc32_string (0, name), crc32_string (0, get_random_seed (false))); @@ -6809,6 +7001,7 @@ get_file_function_name (const char *type) p = q; } + clean_symbol_name (q); buf = (char *) alloca (sizeof (FILE_FUNCTION_FORMAT) + strlen (p) + strlen (type)); @@ -7103,7 +7296,7 @@ make_vector_type (tree innertype, int nunits, enum machine_mode mode) t = make_node (VECTOR_TYPE); TREE_TYPE (t) = TYPE_MAIN_VARIANT (innertype); SET_TYPE_VECTOR_SUBPARTS (t, nunits); - TYPE_MODE (t) = mode; + SET_TYPE_MODE (t, mode); TYPE_READONLY (t) = TYPE_READONLY (innertype); TYPE_VOLATILE (t) = TYPE_VOLATILE (innertype); @@ -7360,19 +7553,19 @@ build_common_tree_nodes_2 (int short_double) dfloat32_type_node = make_node (REAL_TYPE); TYPE_PRECISION (dfloat32_type_node) = DECIMAL32_TYPE_SIZE; layout_type (dfloat32_type_node); - TYPE_MODE (dfloat32_type_node) = SDmode; + SET_TYPE_MODE (dfloat32_type_node, SDmode); dfloat32_ptr_type_node = build_pointer_type (dfloat32_type_node); dfloat64_type_node = make_node (REAL_TYPE); TYPE_PRECISION (dfloat64_type_node) = DECIMAL64_TYPE_SIZE; layout_type (dfloat64_type_node); - TYPE_MODE (dfloat64_type_node) = DDmode; + SET_TYPE_MODE (dfloat64_type_node, DDmode); dfloat64_ptr_type_node = build_pointer_type (dfloat64_type_node); dfloat128_type_node = make_node (REAL_TYPE); TYPE_PRECISION (dfloat128_type_node) = DECIMAL128_TYPE_SIZE; layout_type (dfloat128_type_node); - TYPE_MODE (dfloat128_type_node) = TDmode; + SET_TYPE_MODE (dfloat128_type_node, TDmode); dfloat128_ptr_type_node = build_pointer_type (dfloat128_type_node); complex_integer_type_node = build_complex_type (integer_type_node);