> Ah - tree_ssa_useless_type_conversion and callers, during gimplification.
> I'd like to get rid of it but maybe simply delete the VIEW_CONVERT_EXPR
> case from it for now (and return true unconditionally for NON_LVALUE_EXPR).
> 
> Index: gcc/tree-ssa.c
> ===================================================================
> --- gcc/tree-ssa.c      (revision 229517)
> +++ gcc/tree-ssa.c      (working copy)
> @@ -1142,13 +1161,16 @@ delete_tree_ssa (struct function *fn)
>  bool
>  tree_ssa_useless_type_conversion (tree expr)
>  {
> +  /* Not strictly a conversion but this function is used to strip
> +     useless stuff from trees returned from GENERIC folding.  */
> +  if (TREE_CODE (expr) == NON_LVALUE_EXPR)
> +    return true;
> +
>    /* If we have an assignment that merely uses a NOP_EXPR to change
>       the top of the RHS to the type of the LHS and the type conversion
>       is "safe", then strip away the type conversion so that we can
>       enter LHS = RHS into the const_and_copies table.  */
> -  if (CONVERT_EXPR_P (expr)
> -      || TREE_CODE (expr) == VIEW_CONVERT_EXPR
> -      || TREE_CODE (expr) == NON_LVALUE_EXPR)
> +  if (CONVERT_EXPR_P (expr))
>      return useless_type_conversion_p
>        (TREE_TYPE (expr),
>         TREE_TYPE (TREE_OPERAND (expr, 0)));

The patch introduces GIMPLE checking failures:

FAIL:   c52103m
FAIL:   c52103r
FAIL:   c52104m
FAIL:   c52104r

of the form:

slice9.adb: In function 'Slice9':
slice9.adb:1:1: error: conversion of an SSA_NAME on the left hand side
VIEW_CONVERT_EXPR<character[D.4195:iftmp.10]>("ABCDE");

D.4379 = &VIEW_CONVERT_EXPR<character[D.4195:iftmp.10]>("ABCDE")[D.4378 ...]
{lb: D.4195 sz: 1};

      if (TREE_CODE (expr) == VIEW_CONVERT_EXPR)
        {
          /* For VIEW_CONVERT_EXPRs which are allowed here too, we only check
             that their operand is not an SSA name or an invariant when
             requiring an lvalue (this usually means there is a SRA or IPA-SRA
             bug).  Otherwise there is nothing to verify, gross mismatches at
             most invoke undefined behavior.  */
          if (require_lvalue
              && (TREE_CODE (op) == SSA_NAME
                  || is_gimple_min_invariant (op)))
            {
              error ("conversion of an SSA_NAME on the left hand side");
              debug_generic_stmt (expr);
              return true;
            }
          else if (TREE_CODE (op) == SSA_NAME
                && TYPE_SIZE (TREE_TYPE (expr)) != TYPE_SIZE (TREE_TYPE (op)))
            {
              error ("conversion of register to a different size");
              debug_generic_stmt (expr);
              return true;
            }
          else if (!handled_component_p (op))
            return false;
        }

It's related to dynamic slicing (reduced testcase attached).


        * gnat.dg/slice9.adb: New test.

-- 
Eric Botcazou
-- { dg-do compile }

procedure Slice9 is

  function Ident (I : Integer) return Integer is
  begin
    return I;
  end;

  subtype S is String (Ident(5)..Ident(9));

  Dest : S;

  Src : String (Ident(1)..Ident(5)) := "ABCDE";

begin
  Dest (Ident(5)..Ident(7)) := Src (Ident(1)..Ident(3));
end;

Reply via email to