https://gcc.gnu.org/bugzilla/show_bug.cgi?id=67170

--- Comment #4 from Richard Biener <rguenth at gcc dot gnu.org> ---
Corrected variant, we hit the assert I put in the first one.

Index: gcc/tree-ssa-alias.c
===================================================================
--- gcc/tree-ssa-alias.c        (revision 226852)
+++ gcc/tree-ssa-alias.c        (working copy)
@@ -2153,6 +2153,37 @@ call_may_clobber_ref_p_1 (gcall *call, a
        return false;
     }

+  /* If the base of an indirect access is a parameter which by means
+     of the fnspec of ourselves not clobbered by us then it is surely
+     not modified by calls we do.  */
+  tree base_ptr;
+  tree fnspec;
+  if (TREE_CODE (base) == MEM_REF
+      && (base_ptr = TREE_OPERAND (base, 0))
+      && TREE_CODE (base_ptr) == SSA_NAME
+      && SSA_NAME_IS_DEFAULT_DEF (base_ptr)
+      && SSA_NAME_VAR (base_ptr)
+      && TREE_CODE (SSA_NAME_VAR (base_ptr)) == PARM_DECL
+      && (fnspec = lookup_attribute ("fn spec",
+                                    TYPE_ATTRIBUTES (TREE_TYPE
(cfun->decl)))))
+    {
+      unsigned i = 0;
+      tree arg;
+      for (arg = DECL_ARGUMENTS (cfun->decl);
+          arg && arg != SSA_NAME_VAR (base_ptr); arg = DECL_CHAIN (arg), ++i)
+       ;
+      /* The static chain is a PARM_DECL as well for example so we may
+        not be able to find base_ptr in the list of arguments.  */
+      if (arg == SSA_NAME_VAR (base_ptr))
+       {
+         fnspec = TREE_VALUE (TREE_VALUE (fnspec));
+         if ((unsigned) TREE_STRING_LENGTH (fnspec) > i + 1
+             && (TREE_STRING_POINTER (fnspec)[i + 1] == 'R'
+                 || TREE_STRING_POINTER (fnspec)[i + 1] == 'r'))
+           return false;
+       }
+    }
+
   /* Check if the base variable is call-clobbered.  */
   if (DECL_P (base))
     return pt_solution_includes (gimple_call_clobber_set (call), base);

Reply via email to