On Fri, Jun 30, 2023 at 7:46 AM Kewen.Lin <li...@linux.ibm.com> wrote: > > Hi, > > As PR110248 shows, to get the expected query results for > that case internal functions LEN_{LOAD,STORE} is unable to > adopt some addressing modes, we need to pass down the > related IFN code as well. This patch is to make IVOPTs > pass down ifn code for USE_PTR_ADDRESS type uses, it > adjusts the related {strict_,}memory_address_addr_space_p > and valid_mem_ref_p functions as well. > > Bootstrapped and regtested on x86_64-redhat-linux and > powerpc64{,le}-linux-gnu. > > Is it ok for trunk?
LGTM. > BR, > Kewen > ----- > PR tree-optimization/110248 > > gcc/ChangeLog: > > * recog.cc (memory_address_addr_space_p): Add one more argument ch of > type code_helper and pass it to > targetm.addr_space.legitimate_address_p > instead of ERROR_MARK. > (offsettable_address_addr_space_p): Update one function pointer with > one more argument of type code_helper as its assignees > memory_address_addr_space_p and strict_memory_address_addr_space_p > have been adjusted, and adjust some call sites with ERROR_MARK. > * recog.h (tree.h): New include header file for tree_code ERROR_MARK. > (memory_address_addr_space_p): Adjust with one more unnamed argument > of type code_helper with default ERROR_MARK. > (strict_memory_address_addr_space_p): Likewise. > * reload.cc (strict_memory_address_addr_space_p): Add one unnamed > argument of type code_helper. > * tree-ssa-address.cc (valid_mem_ref_p): Add one more argument ch of > type code_helper and pass it to memory_address_addr_space_p. > * tree-ssa-address.h (valid_mem_ref_p): Adjust the declaration with > one more unnamed argument of type code_helper with default value > ERROR_MARK. > * tree-ssa-loop-ivopts.cc (get_address_cost): Use ERROR_MARK as code > by default, change it with ifn code for USE_PTR_ADDRESS type use, and > pass it to all valid_mem_ref_p calls. > --- > gcc/recog.cc | 13 ++++++------- > gcc/recog.h | 10 +++++++--- > gcc/reload.cc | 2 +- > gcc/tree-ssa-address.cc | 4 ++-- > gcc/tree-ssa-address.h | 3 ++- > gcc/tree-ssa-loop-ivopts.cc | 18 +++++++++++++----- > 6 files changed, 31 insertions(+), 19 deletions(-) > > diff --git a/gcc/recog.cc b/gcc/recog.cc > index 692c258def6..2bff6c03e4d 100644 > --- a/gcc/recog.cc > +++ b/gcc/recog.cc > @@ -1802,8 +1802,8 @@ pop_operand (rtx op, machine_mode mode) > for mode MODE in address space AS. */ > > bool > -memory_address_addr_space_p (machine_mode mode ATTRIBUTE_UNUSED, > - rtx addr, addr_space_t as) > +memory_address_addr_space_p (machine_mode mode ATTRIBUTE_UNUSED, rtx addr, > + addr_space_t as, code_helper ch) > { > #ifdef GO_IF_LEGITIMATE_ADDRESS > gcc_assert (ADDR_SPACE_GENERIC_P (as)); > @@ -1813,8 +1813,7 @@ memory_address_addr_space_p (machine_mode mode > ATTRIBUTE_UNUSED, > win: > return true; > #else > - return targetm.addr_space.legitimate_address_p (mode, addr, 0, as, > - ERROR_MARK); > + return targetm.addr_space.legitimate_address_p (mode, addr, 0, as, ch); > #endif > } > > @@ -2430,7 +2429,7 @@ offsettable_address_addr_space_p (int strictp, > machine_mode mode, rtx y, > rtx z; > rtx y1 = y; > rtx *y2; > - bool (*addressp) (machine_mode, rtx, addr_space_t) = > + bool (*addressp) (machine_mode, rtx, addr_space_t, code_helper) = > (strictp ? strict_memory_address_addr_space_p > : memory_address_addr_space_p); > poly_int64 mode_sz = GET_MODE_SIZE (mode); > @@ -2469,7 +2468,7 @@ offsettable_address_addr_space_p (int strictp, > machine_mode mode, rtx y, > *y2 = plus_constant (address_mode, *y2, mode_sz - 1); > /* Use QImode because an odd displacement may be automatically invalid > for any wider mode. But it should be valid for a single byte. */ > - good = (*addressp) (QImode, y, as); > + good = (*addressp) (QImode, y, as, ERROR_MARK); > > /* In any case, restore old contents of memory. */ > *y2 = y1; > @@ -2504,7 +2503,7 @@ offsettable_address_addr_space_p (int strictp, > machine_mode mode, rtx y, > > /* Use QImode because an odd displacement may be automatically invalid > for any wider mode. But it should be valid for a single byte. */ > - return (*addressp) (QImode, z, as); > + return (*addressp) (QImode, z, as, ERROR_MARK); > } > > /* Return true if ADDR is an address-expression whose effect depends > diff --git a/gcc/recog.h b/gcc/recog.h > index badf8e3dc1c..c6ef619c5dd 100644 > --- a/gcc/recog.h > +++ b/gcc/recog.h > @@ -20,6 +20,9 @@ along with GCC; see the file COPYING3. If not see > #ifndef GCC_RECOG_H > #define GCC_RECOG_H > > +/* For enum tree_code ERROR_MARK. */ > +#include "tree.h" > + > /* Random number that should be large enough for all purposes. Also define > a type that has at least MAX_RECOG_ALTERNATIVES + 1 bits, with the extra > bit giving an invalid value that can be used to mean "uninitialized". */ > @@ -200,11 +203,12 @@ extern void temporarily_undo_changes (int); > extern void redo_changes (int); > extern bool constrain_operands (int, alternative_mask); > extern bool constrain_operands_cached (rtx_insn *, int); > -extern bool memory_address_addr_space_p (machine_mode, rtx, addr_space_t); > +extern bool memory_address_addr_space_p (machine_mode, rtx, addr_space_t, > + code_helper = ERROR_MARK); > #define memory_address_p(mode,addr) \ > memory_address_addr_space_p ((mode), (addr), ADDR_SPACE_GENERIC) > -extern bool strict_memory_address_addr_space_p (machine_mode, rtx, > - addr_space_t); > +extern bool strict_memory_address_addr_space_p (machine_mode, rtx, > addr_space_t, > + code_helper = ERROR_MARK); > #define strict_memory_address_p(mode,addr) \ > strict_memory_address_addr_space_p ((mode), (addr), > ADDR_SPACE_GENERIC) > extern bool validate_replace_rtx_subexp (rtx, rtx, rtx_insn *, rtx *); > diff --git a/gcc/reload.cc b/gcc/reload.cc > index 0be21f7b61e..2126bdd117c 100644 > --- a/gcc/reload.cc > +++ b/gcc/reload.cc > @@ -2162,7 +2162,7 @@ hard_reg_set_here_p (unsigned int beg_regno, unsigned > int end_regno, rtx x) > > bool > strict_memory_address_addr_space_p (machine_mode mode ATTRIBUTE_UNUSED, > - rtx addr, addr_space_t as) > + rtx addr, addr_space_t as, code_helper) > { > #ifdef GO_IF_LEGITIMATE_ADDRESS > gcc_assert (ADDR_SPACE_GENERIC_P (as)); > diff --git a/gcc/tree-ssa-address.cc b/gcc/tree-ssa-address.cc > index 0aaddde8d02..b942799f6f5 100644 > --- a/gcc/tree-ssa-address.cc > +++ b/gcc/tree-ssa-address.cc > @@ -344,7 +344,7 @@ tree_mem_ref_addr (tree type, tree mem_ref) > > bool > valid_mem_ref_p (machine_mode mode, addr_space_t as, > - struct mem_address *addr) > + struct mem_address *addr, code_helper ch) > { > rtx address; > > @@ -352,7 +352,7 @@ valid_mem_ref_p (machine_mode mode, addr_space_t as, > if (!address) > return false; > > - return memory_address_addr_space_p (mode, address, as); > + return memory_address_addr_space_p (mode, address, as, ch); > } > > /* Checks whether a TARGET_MEM_REF with type TYPE and parameters given by > ADDR > diff --git a/gcc/tree-ssa-address.h b/gcc/tree-ssa-address.h > index 2eadbdef810..faa1cb13745 100644 > --- a/gcc/tree-ssa-address.h > +++ b/gcc/tree-ssa-address.h > @@ -31,7 +31,8 @@ extern rtx addr_for_mem_ref (struct mem_address *, > addr_space_t, bool); > extern rtx addr_for_mem_ref (tree exp, addr_space_t as, bool really_expand); > extern void get_address_description (tree, struct mem_address *); > extern tree tree_mem_ref_addr (tree, tree); > -extern bool valid_mem_ref_p (machine_mode, addr_space_t, struct mem_address > *); > +extern bool valid_mem_ref_p (machine_mode, addr_space_t, struct mem_address > *, > + code_helper = ERROR_MARK); > extern void move_fixed_address_to_symbol (struct mem_address *, > class aff_tree *); > tree create_mem_ref (gimple_stmt_iterator *, tree, > diff --git a/gcc/tree-ssa-loop-ivopts.cc b/gcc/tree-ssa-loop-ivopts.cc > index 6671ff6db5a..30b69a31d0f 100644 > --- a/gcc/tree-ssa-loop-ivopts.cc > +++ b/gcc/tree-ssa-loop-ivopts.cc > @@ -4696,17 +4696,25 @@ get_address_cost (struct ivopts_data *data, struct > iv_use *use, > /* Only true if ratio != 1. */ > bool ok_with_ratio_p = false; > bool ok_without_ratio_p = false; > + code_helper code = ERROR_MARK; > + > + if (use->type == USE_PTR_ADDRESS) > + { > + gcall *call = as_a<gcall *> (use->stmt); > + gcc_assert (gimple_call_internal_p (call)); > + code = gimple_call_internal_fn (call); > + } > > if (!aff_combination_const_p (aff_inv)) > { > parts.index = integer_one_node; > /* Addressing mode "base + index". */ > - ok_without_ratio_p = valid_mem_ref_p (mem_mode, as, &parts); > + ok_without_ratio_p = valid_mem_ref_p (mem_mode, as, &parts, code); > if (ratio != 1) > { > parts.step = wide_int_to_tree (type, ratio); > /* Addressing mode "base + index << scale". */ > - ok_with_ratio_p = valid_mem_ref_p (mem_mode, as, &parts); > + ok_with_ratio_p = valid_mem_ref_p (mem_mode, as, &parts, code); > if (!ok_with_ratio_p) > parts.step = NULL_TREE; > } > @@ -4716,7 +4724,7 @@ get_address_cost (struct ivopts_data *data, struct > iv_use *use, > { > parts.offset = wide_int_to_tree (sizetype, aff_inv->offset); > /* Addressing mode "base + index [<< scale] + offset". */ > - if (!valid_mem_ref_p (mem_mode, as, &parts)) > + if (!valid_mem_ref_p (mem_mode, as, &parts, code)) > parts.offset = NULL_TREE; > else > aff_inv->offset = 0; > @@ -4729,7 +4737,7 @@ get_address_cost (struct ivopts_data *data, struct > iv_use *use, > > /* Addressing mode "symbol + base + index [<< scale] [+ offset]". > */ > if (parts.symbol != NULL_TREE > - && !valid_mem_ref_p (mem_mode, as, &parts)) > + && !valid_mem_ref_p (mem_mode, as, &parts, code)) > { > aff_combination_add_elt (aff_inv, parts.symbol, 1); > parts.symbol = NULL_TREE; > @@ -4767,7 +4775,7 @@ get_address_cost (struct ivopts_data *data, struct > iv_use *use, > { > parts.offset = wide_int_to_tree (sizetype, aff_inv->offset); > /* Addressing mode "base + offset". */ > - if (!valid_mem_ref_p (mem_mode, as, &parts)) > + if (!valid_mem_ref_p (mem_mode, as, &parts, code)) > parts.offset = NULL_TREE; > else > aff_inv->offset = 0; > -- > 2.39.3