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

--- Comment #3 from Martin Jambor <jamborm at gcc dot gnu.org> ---
IPA-SRA transformation code gets confused by type mismatch in the K&R
C input, the call has an int where the function has a pointer
parameter and as a consequence we try to obtain an ADDR_EXPR of an SSA
name.

I tend to think the correct thing to do is handle such mismatches by
attempting to convert integers to pointers and just use an undefined
pointer default-def SSA for all other register types - like the patch
below does.  Please speak up if you think that would be a mistake or
if you can think of a better way.  Another option would be to prevent
this situation by gathering (and LTO-streaming) which arguments are
pointers and checking this in WPA.  We'd end up with an extra bitmap
per call which, at least now, seems to me excessive to handle broken
programs.

At the moment I hope that the call to force_gimple_operand_gsi can be
removed fairly easily, however I'd like to do that as a follow-up.

diff --git a/gcc/ipa-param-manipulation.c b/gcc/ipa-param-manipulation.c
index 913b96fefa4..bc175a5541a 100644
--- a/gcc/ipa-param-manipulation.c
+++ b/gcc/ipa-param-manipulation.c
@@ -651,8 +651,26 @@ ipa_param_adjustments::modify_call (gcall *stmt,
       bool deref_base = false;
       unsigned int deref_align = 0;
       if (TREE_CODE (base) != ADDR_EXPR
-         && POINTER_TYPE_P (TREE_TYPE (base)))
-       off = build_int_cst (apm->alias_ptr_type, apm->unit_offset);
+         && is_gimple_reg_type (TREE_TYPE (base)))
+       {
+         /* Detect (gimple register) type mismatches in calls so that we don't
+            ICE.  Make a poor attempt to gracefully treat integers passed in
+            place of pointers, for everything else create a proper undefined
+            value which it is.  */
+         if (INTEGRAL_TYPE_P (TREE_TYPE (base)))
+           {
+             tree tmp = make_ssa_name (ptr_type_node);
+             gassign *convert = gimple_build_assign (tmp, NOP_EXPR, base);
+             gsi_insert_before (&gsi, convert, GSI_SAME_STMT);
+             base = tmp;
+           }
+         else if (!POINTER_TYPE_P (TREE_TYPE (base)))
+           {
+             tree tmp = create_tmp_var (ptr_type_node);
+             base = get_or_create_ssa_default_def (cfun, tmp);
+           }
+         off = build_int_cst (apm->alias_ptr_type, apm->unit_offset);
+       }
       else
        {
          bool addrof;

Reply via email to