From patchwork Sat Nov 23 19:22:47 2013 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Mike Stump X-Patchwork-Id: 293699 Return-Path: X-Original-To: incoming@patchwork.ozlabs.org Delivered-To: patchwork-incoming@bilbo.ozlabs.org Received: from sourceware.org (server1.sourceware.org [209.132.180.131]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (Client did not present a certificate) by ozlabs.org (Postfix) with ESMTPS id EBC692C0097 for ; Sun, 24 Nov 2013 06:38:35 +1100 (EST) DomainKey-Signature: a=rsa-sha1; c=nofws; d=gcc.gnu.org; h=list-id :list-unsubscribe:list-archive:list-post:list-help:sender:from :content-type:subject:date:message-id:cc:to:mime-version; q=dns; s=default; b=w/I7sWmJ87M/lrF9AY8x2vv45Q/isxgtLBFn1Nimmr3ut56Zko /Ow29zLBLQGdcTl75wLg+mHWrU25A/0+T3dVkghzOm9CigpoJLRGGNmGdZvE73Sz JN9SeONYgSsgCrB05sNzDcaaIwqGg7wFJpBnWkH0kBBmXvHRUXMl3CkIg= DKIM-Signature: v=1; a=rsa-sha1; c=relaxed; d=gcc.gnu.org; h=list-id :list-unsubscribe:list-archive:list-post:list-help:sender:from :content-type:subject:date:message-id:cc:to:mime-version; s= default; bh=9CRteNUqMIqPxZXcmbetifepPf8=; b=dA/agEKkqG9Grk/QU90r L8nUSmrYnW7Lb+AXcKSlvAk+hau/Nm1vxmN1CxdO89ihb1qXmii6CwY4iOUEKz7v 55JT5zTF/4G1BPVq1/4YXmSRtQAGZG2CR2NotXv/yh6uSAw1hJFpqkz8Zwv/qJvf Y0kyG1f2KbH99jVdZylhq80= Received: (qmail 2826 invoked by alias); 23 Nov 2013 19:22:57 -0000 Mailing-List: contact gcc-patches-help@gcc.gnu.org; run by ezmlm Precedence: bulk List-Id: List-Unsubscribe: List-Archive: List-Post: List-Help: Sender: gcc-patches-owner@gcc.gnu.org Delivered-To: mailing list gcc-patches@gcc.gnu.org Received: (qmail 2790 invoked by uid 89); 23 Nov 2013 19:22:56 -0000 Authentication-Results: sourceware.org; auth=none X-Virus-Found: No X-Spam-SWARE-Status: No, score=1.0 required=5.0 tests=AWL, BAYES_95, FREEMAIL_FROM, RDNS_NONE, SPF_PASS autolearn=no version=3.3.2 X-HELO: qmta06.emeryville.ca.mail.comcast.net Received: from Unknown (HELO qmta06.emeryville.ca.mail.comcast.net) (76.96.30.56) by sourceware.org (qpsmtpd/0.93/v0.84-503-g423c35a) with ESMTP; Sat, 23 Nov 2013 19:22:55 +0000 Received: from omta20.emeryville.ca.mail.comcast.net ([76.96.30.87]) by qmta06.emeryville.ca.mail.comcast.net with comcast id t6cW1m0011smiN4A67No5y; Sat, 23 Nov 2013 19:22:48 +0000 Received: from up.mrs.kithrup.com ([24.4.193.8]) by omta20.emeryville.ca.mail.comcast.net with comcast id t7NV1m00v0BKwT48g7Nn7M; Sat, 23 Nov 2013 19:22:47 +0000 From: Mike Stump Subject: wide-int, rtl-2 Date: Sat, 23 Nov 2013 11:22:47 -0800 Message-Id: <4198BC58-4C80-4133-A40C-7D5D1478DEF8@comcast.net> Cc: Eric Botcazou , Kenneth Zadeck To: "gcc-patches@gcc.gnu.org Patches" Mime-Version: 1.0 (Mac OS X Mail 6.6 \(1510\)) X-IsSubscribed: yes Richi has asked the we break the wide-int patch so that the individual port and front end maintainers can review their parts without have to go through the entire patch. This patch covers the half of the rtl code. Ok? * dojump.c (prefer_and_bit_test): Use wide-int interfaces. * stmt.c (expand_case): Use wide-int interfaces. * stor-layout.h (set_min_and_max_values_for_integral_type): Take a signop rather than a bool. * stor-layout.c (layout_type): Use wide-int interfaces. (initialize_sizetypes): Update calls to set_min_and_max_values_for_integral_type. (set_min_and_max_values_for_integral_type): Take a signop rather than a bool. Use wide-int interfaces. (fixup_signed_type): Update accordingly. Remove HOST_BITS_PER_DOUBLE_INT limit. (fixup_unsigned_type): Likewise. * varasm.c (decode_addr_const): Use wide-int interfaces. (const_hash_1): Likewise. (const_rtx_hash_1): Likewise (output_constant): Likewise. (array_size_for_constructor): Likewise. (output_constructor_regular_field): Likewise. (output_constructor_bitfield): Likewise. diff --git a/gcc/dojump.c b/gcc/dojump.c index 2aef34d..51c3c8c 100644 --- a/gcc/dojump.c +++ b/gcc/dojump.c @@ -143,6 +143,7 @@ static bool prefer_and_bit_test (enum machine_mode mode, int bitnum) { bool speed_p; + wide_int mask = wi::set_bit_in_zero (bitnum, GET_MODE_PRECISION (mode)); if (and_test == 0) { @@ -163,8 +164,7 @@ prefer_and_bit_test (enum machine_mode mode, int bitnum) } /* Fill in the integers. */ - XEXP (and_test, 1) - = immed_double_int_const (double_int_zero.set_bit (bitnum), mode); + XEXP (and_test, 1) = immed_wide_int_const (mask, mode); XEXP (XEXP (shift_test, 0), 1) = GEN_INT (bitnum); speed_p = optimize_insn_for_speed_p (); diff --git a/gcc/stmt.c b/gcc/stmt.c index 37b2de3..f7d5b4b 100644 --- a/gcc/stmt.c +++ b/gcc/stmt.c @@ -1233,9 +1233,7 @@ expand_case (gimple stmt) original type. Make sure to drop overflow flags. */ low = fold_convert (index_type, low); if (TREE_OVERFLOW (low)) - low = build_int_cst_wide (index_type, - TREE_INT_CST_LOW (low), - TREE_INT_CST_HIGH (low)); + low = wide_int_to_tree (index_type, low); /* The canonical from of a case label in GIMPLE is that a simple case has an empty CASE_HIGH. For the casesi and tablejump expanders, @@ -1244,9 +1242,7 @@ expand_case (gimple stmt) high = low; high = fold_convert (index_type, high); if (TREE_OVERFLOW (high)) - high = build_int_cst_wide (index_type, - TREE_INT_CST_LOW (high), - TREE_INT_CST_HIGH (high)); + high = wide_int_to_tree (index_type, high); basic_block case_bb = label_to_block_fn (cfun, lab); edge case_edge = find_edge (bb, case_bb); diff --git a/gcc/stor-layout.c b/gcc/stor-layout.c index 0a1194e..839a7c2 100644 --- a/gcc/stor-layout.c +++ b/gcc/stor-layout.c @@ -2204,13 +2204,10 @@ layout_type (tree type) && TYPE_UNSIGNED (TREE_TYPE (lb)) && tree_int_cst_lt (ub, lb)) { - unsigned prec = TYPE_PRECISION (TREE_TYPE (lb)); - lb = double_int_to_tree - (ssizetype, - tree_to_double_int (lb).sext (prec)); - ub = double_int_to_tree - (ssizetype, - tree_to_double_int (ub).sext (prec)); + lb = wide_int_to_tree (ssizetype, + offset_int::from (lb, SIGNED)); + ub = wide_int_to_tree (ssizetype, + offset_int::from (ub, SIGNED)); } length = fold_convert (sizetype, @@ -2486,16 +2483,14 @@ initialize_sizetypes (void) TYPE_ALIGN (sizetype) = GET_MODE_ALIGNMENT (TYPE_MODE (sizetype)); TYPE_SIZE (sizetype) = bitsize_int (precision); TYPE_SIZE_UNIT (sizetype) = size_int (GET_MODE_SIZE (TYPE_MODE (sizetype))); - set_min_and_max_values_for_integral_type (sizetype, precision, - /*is_unsigned=*/true); + set_min_and_max_values_for_integral_type (sizetype, precision, UNSIGNED); SET_TYPE_MODE (bitsizetype, smallest_mode_for_size (bprecision, MODE_INT)); TYPE_ALIGN (bitsizetype) = GET_MODE_ALIGNMENT (TYPE_MODE (bitsizetype)); TYPE_SIZE (bitsizetype) = bitsize_int (bprecision); TYPE_SIZE_UNIT (bitsizetype) = size_int (GET_MODE_SIZE (TYPE_MODE (bitsizetype))); - set_min_and_max_values_for_integral_type (bitsizetype, bprecision, - /*is_unsigned=*/true); + set_min_and_max_values_for_integral_type (bitsizetype, bprecision, UNSIGNED); /* Create the signed variants of *sizetype. */ ssizetype = make_signed_type (TYPE_PRECISION (sizetype)); @@ -2515,58 +2510,18 @@ initialize_sizetypes (void) void set_min_and_max_values_for_integral_type (tree type, int precision, - bool is_unsigned) + signop sgn) { - tree min_value; - tree max_value; - /* For bitfields with zero width we end up creating integer types with zero precision. Don't assign any minimum/maximum values to those types, they don't have any valid value. */ if (precision < 1) return; - if (is_unsigned) - { - min_value = build_int_cst (type, 0); - max_value - = build_int_cst_wide (type, precision - HOST_BITS_PER_WIDE_INT >= 0 - ? -1 - : ((HOST_WIDE_INT) 1 << precision) - 1, - precision - HOST_BITS_PER_WIDE_INT > 0 - ? ((unsigned HOST_WIDE_INT) ~0 - >> (HOST_BITS_PER_WIDE_INT - - (precision - HOST_BITS_PER_WIDE_INT))) - : 0); - } - else - { - min_value - = build_int_cst_wide (type, - (precision - HOST_BITS_PER_WIDE_INT > 0 - ? 0 - : (HOST_WIDE_INT) (-1) << (precision - 1)), - (((HOST_WIDE_INT) (-1) - << (precision - HOST_BITS_PER_WIDE_INT - 1 > 0 - ? precision - HOST_BITS_PER_WIDE_INT - 1 - : 0)))); - max_value - = build_int_cst_wide (type, - (precision - HOST_BITS_PER_WIDE_INT > 0 - ? -1 - : (HOST_WIDE_INT) - (((unsigned HOST_WIDE_INT) 1 - << (precision - 1)) - 1)), - (precision - HOST_BITS_PER_WIDE_INT - 1 > 0 - ? (HOST_WIDE_INT) - ((((unsigned HOST_WIDE_INT) 1 - << (precision - HOST_BITS_PER_WIDE_INT - - 1))) - 1) - : 0)); - } - - TYPE_MIN_VALUE (type) = min_value; - TYPE_MAX_VALUE (type) = max_value; + TYPE_MIN_VALUE (type) + = wide_int_to_tree (type, wi::min_value (precision, sgn)); + TYPE_MAX_VALUE (type) + = wide_int_to_tree (type, wi::max_value (precision, sgn)); } /* Set the extreme values of TYPE based on its precision in bits, @@ -2579,14 +2534,7 @@ fixup_signed_type (tree type) { int precision = TYPE_PRECISION (type); - /* We can not represent properly constants greater then - HOST_BITS_PER_DOUBLE_INT, still we need the types - as they are used by i386 vector extensions and friends. */ - if (precision > HOST_BITS_PER_DOUBLE_INT) - precision = HOST_BITS_PER_DOUBLE_INT; - - set_min_and_max_values_for_integral_type (type, precision, - /*is_unsigned=*/false); + set_min_and_max_values_for_integral_type (type, precision, SIGNED); /* Lay out the type: set its alignment, size, etc. */ layout_type (type); @@ -2601,16 +2549,9 @@ fixup_unsigned_type (tree type) { int precision = TYPE_PRECISION (type); - /* We can not represent properly constants greater then - HOST_BITS_PER_DOUBLE_INT, still we need the types - as they are used by i386 vector extensions and friends. */ - if (precision > HOST_BITS_PER_DOUBLE_INT) - precision = HOST_BITS_PER_DOUBLE_INT; - TYPE_UNSIGNED (type) = 1; - set_min_and_max_values_for_integral_type (type, precision, - /*is_unsigned=*/true); + set_min_and_max_values_for_integral_type (type, precision, UNSIGNED); /* Lay out the type: set its alignment, size, etc. */ layout_type (type); diff --git a/gcc/stor-layout.h b/gcc/stor-layout.h index 706bed4..2be020d 100644 --- a/gcc/stor-layout.h +++ b/gcc/stor-layout.h @@ -20,7 +20,7 @@ along with GCC; see the file COPYING3. If not see #ifndef GCC_STOR_LAYOUT_H #define GCC_STOR_LAYOUT_H -extern void set_min_and_max_values_for_integral_type (tree, int, bool); +extern void set_min_and_max_values_for_integral_type (tree, int, signop); extern void fixup_signed_type (tree); extern void internal_reference_types (void); extern unsigned int update_alignment_for_field (record_layout_info, tree, diff --git a/gcc/varasm.c b/gcc/varasm.c index 3ca4700..f627fe9 100644 --- a/gcc/varasm.c +++ b/gcc/varasm.c @@ -2728,7 +2728,7 @@ decode_addr_const (tree exp, struct addr_const *value) else if (TREE_CODE (target) == MEM_REF && TREE_CODE (TREE_OPERAND (target, 0)) == ADDR_EXPR) { - offset += mem_ref_offset (target).low; + offset += mem_ref_offset (target).to_short_addr (); target = TREE_OPERAND (TREE_OPERAND (target, 0), 0); } else if (TREE_CODE (target) == INDIRECT_REF @@ -2808,8 +2808,8 @@ const_hash_1 (const tree exp) switch (code) { case INTEGER_CST: - p = (char *) &TREE_INT_CST (exp); - len = sizeof TREE_INT_CST (exp); + p = (char *) &TREE_INT_CST_ELT (exp, 0); + len = TREE_INT_CST_NUNITS (exp) * sizeof (HOST_WIDE_INT); break; case REAL_CST: @@ -3510,6 +3510,7 @@ const_rtx_hash_1 (rtx *xp, void *data) enum rtx_code code; hashval_t h, *hp; rtx x; + int i; x = *xp; code = GET_CODE (x); @@ -3520,11 +3521,11 @@ const_rtx_hash_1 (rtx *xp, void *data) { case CONST_INT: hwi = INTVAL (x); + fold_hwi: { int shift = sizeof (hashval_t) * CHAR_BIT; const int n = sizeof (HOST_WIDE_INT) / sizeof (hashval_t); - int i; h ^= (hashval_t) hwi; for (i = 1; i < n; ++i) @@ -3535,8 +3536,16 @@ const_rtx_hash_1 (rtx *xp, void *data) } break; + case CONST_WIDE_INT: + hwi = GET_MODE_PRECISION (mode); + { + for (i = 0; i < CONST_WIDE_INT_NUNITS (x); i++) + hwi ^= CONST_WIDE_INT_ELT (x, i); + goto fold_hwi; + } + case CONST_DOUBLE: - if (mode == VOIDmode) + if (TARGET_SUPPORTS_WIDE_INT == 0 && mode == VOIDmode) { hwi = CONST_DOUBLE_LOW (x) ^ CONST_DOUBLE_HIGH (x); goto fold_hwi; @@ -4627,8 +4636,7 @@ output_constant (tree exp, unsigned HOST_WIDE_INT size, unsigned int align) exp = build1 (ADDR_EXPR, saved_type, TREE_OPERAND (exp, 0)); /* Likewise for constant ints. */ else if (TREE_CODE (exp) == INTEGER_CST) - exp = build_int_cst_wide (saved_type, TREE_INT_CST_LOW (exp), - TREE_INT_CST_HIGH (exp)); + exp = wide_int_to_tree (saved_type, exp); } @@ -4768,7 +4776,7 @@ array_size_for_constructor (tree val) tree max_index; unsigned HOST_WIDE_INT cnt; tree index, value, tmp; - double_int i; + offset_int i; /* This code used to attempt to handle string constants that are not arrays of single-bytes, but nothing else does, so there's no point in @@ -4790,14 +4798,13 @@ array_size_for_constructor (tree val) /* Compute the total number of array elements. */ tmp = TYPE_MIN_VALUE (TYPE_DOMAIN (TREE_TYPE (val))); - i = tree_to_double_int (max_index) - tree_to_double_int (tmp); - i += double_int_one; + i = wi::to_offset (max_index) - wi::to_offset (tmp) + 1; /* Multiply by the array element unit size to find number of bytes. */ - i *= tree_to_double_int (TYPE_SIZE_UNIT (TREE_TYPE (TREE_TYPE (val)))); + i *= wi::to_offset (TYPE_SIZE_UNIT (TREE_TYPE (TREE_TYPE (val)))); - gcc_assert (i.fits_uhwi ()); - return i.low; + gcc_assert (wi::fits_uhwi_p (i)); + return i.to_uhwi (); } /* Other datastructures + helpers for output_constructor. */ @@ -4877,11 +4884,10 @@ output_constructor_regular_field (oc_local_state *local) sign-extend the result because Ada has negative DECL_FIELD_OFFSETs but we are using an unsigned sizetype. */ unsigned prec = TYPE_PRECISION (sizetype); - double_int idx = tree_to_double_int (local->index) - - tree_to_double_int (local->min_index); - idx = idx.sext (prec); - fieldpos = (tree_to_uhwi (TYPE_SIZE_UNIT (TREE_TYPE (local->val))) - * idx.low); + offset_int idx = wi::sext (wi::to_offset (local->index) + - wi::to_offset (local->min_index), prec); + fieldpos = (idx * wi::to_offset (TYPE_SIZE_UNIT (TREE_TYPE (local->val)))) + .to_shwi (); } else if (local->field != NULL_TREE) fieldpos = int_byte_position (local->field); @@ -5074,22 +5080,13 @@ output_constructor_bitfield (oc_local_state *local, unsigned int bit_offset) the word boundary in the INTEGER_CST. We can only select bits from the LOW or HIGH part not from both. */ - if (shift < HOST_BITS_PER_WIDE_INT - && shift + this_time > HOST_BITS_PER_WIDE_INT) - { - this_time = shift + this_time - HOST_BITS_PER_WIDE_INT; - shift = HOST_BITS_PER_WIDE_INT; - } + if ((shift / HOST_BITS_PER_WIDE_INT) + != ((shift + this_time) / HOST_BITS_PER_WIDE_INT)) + this_time = (shift + this_time) & (HOST_BITS_PER_WIDE_INT - 1); /* Now get the bits from the appropriate constant word. */ - if (shift < HOST_BITS_PER_WIDE_INT) - value = TREE_INT_CST_LOW (local->val); - else - { - gcc_assert (shift < HOST_BITS_PER_DOUBLE_INT); - value = TREE_INT_CST_HIGH (local->val); - shift -= HOST_BITS_PER_WIDE_INT; - } + value = TREE_INT_CST_ELT (local->val, shift / HOST_BITS_PER_WIDE_INT); + shift = shift & (HOST_BITS_PER_WIDE_INT - 1); /* Get the result. This works only when: 1 <= this_time <= HOST_BITS_PER_WIDE_INT. */ @@ -5109,19 +5106,13 @@ output_constructor_bitfield (oc_local_state *local, unsigned int bit_offset) the word boundary in the INTEGER_CST. We can only select bits from the LOW or HIGH part not from both. */ - if (shift < HOST_BITS_PER_WIDE_INT - && shift + this_time > HOST_BITS_PER_WIDE_INT) + if ((shift / HOST_BITS_PER_WIDE_INT) + != ((shift + this_time) / HOST_BITS_PER_WIDE_INT)) this_time = (HOST_BITS_PER_WIDE_INT - shift); /* Now get the bits from the appropriate constant word. */ - if (shift < HOST_BITS_PER_WIDE_INT) - value = TREE_INT_CST_LOW (local->val); - else - { - gcc_assert (shift < HOST_BITS_PER_DOUBLE_INT); - value = TREE_INT_CST_HIGH (local->val); - shift -= HOST_BITS_PER_WIDE_INT; - } + value = TREE_INT_CST_ELT (local->val, shift / HOST_BITS_PER_WIDE_INT); + shift = shift & (HOST_BITS_PER_WIDE_INT - 1); /* Get the result. This works only when: 1 <= this_time <= HOST_BITS_PER_WIDE_INT. */