From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: by sourceware.org (Postfix, from userid 48) id D277C3858418; Tue, 8 Mar 2022 17:25:08 +0000 (GMT) DKIM-Filter: OpenDKIM Filter v2.11.0 sourceware.org D277C3858418 From: "law at gcc dot gnu.org" To: gcc-bugs@gcc.gnu.org Subject: [Bug tree-optimization/40073] Vector short/char shifts generate sub-optimal code Date: Tue, 08 Mar 2022 17:25:08 +0000 X-Bugzilla-Reason: CC X-Bugzilla-Type: changed X-Bugzilla-Watch-Reason: None X-Bugzilla-Product: gcc X-Bugzilla-Component: tree-optimization X-Bugzilla-Version: 6.0 X-Bugzilla-Keywords: missed-optimization X-Bugzilla-Severity: enhancement X-Bugzilla-Who: law at gcc dot gnu.org X-Bugzilla-Status: NEW X-Bugzilla-Resolution: X-Bugzilla-Priority: P3 X-Bugzilla-Assigned-To: unassigned at gcc dot gnu.org X-Bugzilla-Target-Milestone: --- X-Bugzilla-Flags: X-Bugzilla-Changed-Fields: Message-ID: In-Reply-To: References: Content-Type: text/plain; charset="UTF-8" Content-Transfer-Encoding: quoted-printable X-Bugzilla-URL: http://gcc.gnu.org/bugzilla/ Auto-Submitted: auto-generated MIME-Version: 1.0 X-BeenThere: gcc-bugs@gcc.gnu.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: Gcc-bugs mailing list List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-List-Received-Date: Tue, 08 Mar 2022 17:25:08 -0000 https://gcc.gnu.org/bugzilla/show_bug.cgi?id=3D40073 --- Comment #19 from Jeffrey A. Law --- I stumbled over this as well as some point. One thing I started playing w= ith, but had to set aside was making vect_get_range_info smarter. In particular the case I was looking at VAR would have a single use that wa= s a narrowing conversion. Taking advantage of that narrowing conversion would = tend to allow us to use VxQI and VxHI shifts more often. It's just something we noticed, but never chased down if it was important in terms of real world code generation. I see two patches in my stash. No id= ea the state on either one, but they might point you at something useful... diff --git a/gcc/tree-vect-patterns.c b/gcc/tree-vect-patterns.c index 803de3fc287..43369eb8f4e 100644 --- a/gcc/tree-vect-patterns.c +++ b/gcc/tree-vect-patterns.c @@ -58,6 +58,37 @@ vect_get_range_info (tree var, wide_int *min_value, wide= _int *max_value) value_range_kind vr_type =3D get_range_info (var, min_value, max_value); wide_int nonzero =3D get_nonzero_bits (var); signop sgn =3D TYPE_SIGN (TREE_TYPE (var)); + + /* If VAR has a single use in a narrowing conversion, then we may be + able to use the narrowing conversion to get a tighter range. */ + gimple *use_stmt; + use_operand_p use; + if (vr_type =3D=3D VR_VARYING + && single_imm_use (var, &use, &use_stmt) + && is_gimple_assign (use_stmt) + && gimple_assign_rhs_code (use_stmt) =3D=3D NOP_EXPR) + { + /* We know VAR has a single use that is a conversion. Now check + if it is a narrowing conversion. */ + tree lhs =3D gimple_assign_lhs (use_stmt); + unsigned HOST_WIDE_INT orig_size =3D tree_to_uhwi (TYPE_SIZE (TREE_T= YPE (var))); + unsigned HOST_WIDE_INT lhs_size =3D tree_to_uhwi (TYPE_SIZE (TREE_TY= PE (lhs))); + + if (lhs_size < orig_size) + { + /* The single use of VAR was a narrowing conversion. + Use the nonzero bits from the narrower type and + the min/max values of VAR's type. + + This allows the intersect call below to work in the expected w= ay.=20 */ + nonzero =3D get_nonzero_bits (lhs); + sgn =3D TYPE_SIGN (TREE_TYPE (lhs)); + *min_value =3D wi::to_wide (vrp_val_min (TREE_TYPE (lhs))); + *max_value =3D wi::to_wide (vrp_val_min (TREE_TYPE (lhs))); + vr_type =3D VR_RANGE; + } + } + if (intersect_range_with_nonzero_bits (vr_type, min_value, max_value, nonzero, sgn) =3D=3D VR_RANGE) { And another variant: @@ -74,6 +74,38 @@ vect_get_range_info (tree var, wide_int *min_value, wide= _int *max_value) } else { + /* Try a bit harder to get a narrowed range. If VAR has a single use that + is a conversion, see if we can use the converted range. */ + gimple *stmt; + use_operand_p use; + if (single_imm_use (var, &use, &stmt) + && is_gimple_assign (stmt) + && gimple_assign_rhs_code (stmt) =3D=3D NOP_EXPR) + { + /* If this is a narrowing conversion, then we win as it + narrows the range of VAR. */ + tree lhs =3D gimple_assign_lhs (stmt); + unsigned HOST_WIDE_INT orig_size =3D tree_to_uhwi (TYPE_SIZE (TRE= E_TYPE (var))); + unsigned HOST_WIDE_INT lhs_size =3D tree_to_uhwi (TYPE_SIZE (TREE= _TYPE (lhs))); + if (lhs_size < orig_size) + { + *min_value =3D wi::to_wide (TYPE_MIN_VALUE (TREE_TYPE (lhs))); + *max_value =3D wi::to_wide (TYPE_MAX_VALUE (TREE_TYPE (lhs))); + if (dump_enabled_p ()) + { + dump_generic_expr_loc (MSG_NOTE, vect_location, TDF_SLIM, var); + dump_printf (MSG_NOTE, " has range ["); + dump_hex (MSG_NOTE, *min_value); + dump_printf (MSG_NOTE, ", "); + dump_hex (MSG_NOTE, *max_value); + dump_printf (MSG_NOTE, "]\n"); + } + return true; + } + + + } + if (dump_enabled_p ()) { dump_generic_expr_loc (MSG_NOTE, vect_location, TDF_SLIM, var);=