From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: by sourceware.org (Postfix, from userid 2049) id 5AADB385383F; Fri, 21 Oct 2022 13:21:34 +0000 (GMT) DKIM-Filter: OpenDKIM Filter v2.11.0 sourceware.org 5AADB385383F DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gcc.gnu.org; s=default; t=1666358494; bh=ONiixsicaBpHnWcgJZ9LICt23q088DG+jxUBaXFhuUU=; h=From:To:Subject:Date:From; b=Vgwp7ehMLdWFzKg9+UBqn/gvRuZhGL7WorEGKVnR0kK3uJco5GMkswy85hU3fc5fz Hr55dM81/cf8iOIuL6RXkJpRIDhSSKiSvLmuRddKquYO+gLSOKG9GOOlGZnTnGggx+ HSlKZEFl4FMPe7lsZCLl81RCf4UFaLmP6/NwCIuw= Content-Type: text/plain; charset="us-ascii" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit From: Matthew Malcomson To: gcc-cvs@gcc.gnu.org Subject: [gcc(refs/vendors/ARM/heads/morello)] Add folding for replace_address_value X-Act-Checkin: gcc X-Git-Author: Matthew Malcomson X-Git-Refname: refs/vendors/ARM/heads/morello X-Git-Oldrev: 5e73df0637dbdfa3bf0b3e35f2b406d6841c1979 X-Git-Newrev: 5ecdb56f3dcea8d16b9d60bae90a0af35990f194 Message-Id: <20221021132134.5AADB385383F@sourceware.org> Date: Fri, 21 Oct 2022 13:21:34 +0000 (GMT) List-Id: https://gcc.gnu.org/g:5ecdb56f3dcea8d16b9d60bae90a0af35990f194 commit 5ecdb56f3dcea8d16b9d60bae90a0af35990f194 Author: Matthew Malcomson Date: Fri Oct 21 14:18:49 2022 +0100 Add folding for replace_address_value This failure to fold a REPLACE_ADDRESS_VALUE internal function call was causing some test failures in the libstdc++ testsuite when using an integer casted to a pointer as a parameter in a builtin function call that the testcase required to get folded away. The initial call to `fold_build_replace_address_value_loc` is made with a relatively complex tree as its argument (the "capability value" is given as the negate_expr of a constant) which is something that we really don't want to have to handle. However it seems that in the C++ frontend more folding is attempted later on. This folding is attempted using the general function `fold` defined in fold-const.c. This is called via `cp_fold`. If we simply allow this function to handle the same sort of a REPLACE_ADDRESS_VALUE on INTEGER_CST arguments that we already handle while building the internal function call then we observe that the required folding happens. N.b. based on some comments in `c_fully_fold_internal`, I believe that handling replace_address_value in `fold` was not necessary for the C language since the C language already handled all folding of function arguments while building the expression up. Hence this does not appear to have changed the C frontend behaviour. Diff: --- gcc/fold-const.c | 57 +++++++++++++++++++++++++++++++++++++++----------------- gcc/fold-const.h | 1 + 2 files changed, 41 insertions(+), 17 deletions(-) diff --git a/gcc/fold-const.c b/gcc/fold-const.c index 39cd66af522..e551cc7c216 100644 --- a/gcc/fold-const.c +++ b/gcc/fold-const.c @@ -13026,7 +13026,11 @@ fold (tree expr) { if (code == CALL_EXPR) { - tem = fold_call_expr (loc, expr, false); + if (CALL_EXPR_FN (expr) == NULL_TREE + && CALL_EXPR_IFN (expr) == IFN_REPLACE_ADDRESS_VALUE) + tem = fold_replace_address_value_loc (loc, expr); + else + tem = fold_call_expr (loc, expr, false); return tem ? tem : expr; } return expr; @@ -13638,27 +13642,21 @@ fold_build_call_array_initializer_loc (location_t loc, tree type, tree fn, #undef START_FOLD_INIT #undef END_FOLD_INIT -/* Build REPLACE_ADDRESS_VALUE internal function, folding away constant - assignments if possible. - - We currently only fold away assignments to a constant 0 capability to make - constant integer initialisation work nicely, but this could be made to work - on assignments to any integer_cst capability. */ +/* Helper for both fold_build_replace_address_value_loc and + fold_build_replace_address_value. This implements the folding for both. -tree -fold_build_replace_address_value_loc (location_t loc, tree c, tree cv) + We only handle expressions which we know are constants. */ +static tree +fold_replace_address_value_1 (location_t loc, tree c, tree cv) { - if (! tree_is_capability_value (c)) - return fold_convert (TREE_TYPE (c), cv); - gcc_assert (INTEGRAL_TYPE_P (TREE_TYPE (cv)) - && TYPE_PRECISION (TREE_TYPE (cv)) - <= TYPE_PRECISION (noncapability_type (TREE_TYPE (c)))); - - tree orig_c = c; tree orig_cv = cv; STRIP_ANY_LOCATION_WRAPPER (c); STRIP_ANY_LOCATION_WRAPPER (cv); + gcc_assert (INTEGRAL_TYPE_P (TREE_TYPE (cv)) + && TYPE_PRECISION (TREE_TYPE (cv)) + <= TYPE_PRECISION (noncapability_type (TREE_TYPE (c)))); + if (TREE_CODE (c) == INTEGER_CST && TREE_CODE (cv) == INTEGER_CST) { tree cap_type = TREE_TYPE (c); @@ -13690,7 +13688,32 @@ fold_build_replace_address_value_loc (location_t loc, tree c, tree cv) CALL_EXPR_ARG (c, 0), orig_cv); } - return build_replace_address_value_loc (loc, orig_c, orig_cv); + return NULL_TREE; +} + +/* Build REPLACE_ADDRESS_VALUE internal function, folding away constant + assignments if possible. */ +tree +fold_build_replace_address_value_loc (location_t loc, tree c, tree cv) +{ + if (! tree_is_capability_value (c)) + return fold_convert (TREE_TYPE (c), cv); + + tree tmp = fold_replace_address_value_1 (loc, c, cv); + if (tmp) + return tmp; + + return build_replace_address_value_loc (loc, c, cv); +} + +/* Fold a REPLACE_ADDRESS_VALUE internal function call, folding away constant + assignments and constant recursive calls. */ +tree +fold_replace_address_value_loc (location_t loc, tree exp) +{ + tree c = CALL_EXPR_ARG (exp, 0); + tree cv = CALL_EXPR_ARG (exp, 1); + return fold_replace_address_value_1 (loc, c, cv); } tree diff --git a/gcc/fold-const.h b/gcc/fold-const.h index 738e2d0fc51..904e01dd9f0 100644 --- a/gcc/fold-const.h +++ b/gcc/fold-const.h @@ -79,6 +79,7 @@ extern tree get_array_ctor_element_at_index (tree, offset_int, #define fold_build_replace_address_value(T1, T2)\ fold_build_replace_address_value_loc (UNKNOWN_LOCATION, T1, T2) extern tree fold_build_replace_address_value_loc (location_t, tree, tree); +extern tree fold_replace_address_value_loc (location_t, tree); extern tree maybe_cap_int_const_binop (tree_code, tree, tree); extern bool fold_convertible_p (const_tree, const_tree); #define fold_convert(T1,T2)\