On Wed, Jan 20, 2016 at 10:41:47AM +0100, Richard Biener wrote:
> > We already do diagnose tons of other cases for inline asm at
> > gimplification time.  I can replace the error with a warning followed by
> > copying it to addressable memory, that seems to be what the older gccs were
> > doing during expansion after issuing above mentioned warning.
> 
> That sounds better then though it would be nice to warn from the FE
> somehow.

Like this?  I'm afraid I don't know how to find out if it is a case we can
or can't handle better at the FE side.

2016-01-20  Jakub Jelinek  <ja...@redhat.com>

        PR middle-end/67653
        * gimplify.c (gimplify_asm_expr): Warn if it is too late to
        attempt to mark memory input operand addressable and
        call prepare_gimple_addressable in that case.  Don't adjust
        input_location for diagnostics, use error_at instead.

        * c-c++-common/pr67653.c: New test.
        * gcc.dg/torture/pr29119.c: Add dg-warning.

--- gcc/gimplify.c.jj   2016-01-19 09:20:22.467792253 +0100
+++ gcc/gimplify.c      2016-01-20 14:44:17.571333221 +0100
@@ -5305,12 +5305,41 @@ gimplify_asm_expr (tree *expr_p, gimple_
            TREE_VALUE (link) = error_mark_node;
          tret = gimplify_expr (&TREE_VALUE (link), pre_p, post_p,
                                is_gimple_lvalue, fb_lvalue | fb_mayfail);
+         if (tret != GS_ERROR)
+           {
+             /* Unlike output operands, memory inputs are not guaranteed
+                to be lvalues by the FE, and while the expressions are
+                marked addressable there, if it is e.g. a statement
+                expression, temporaries in it might not end up being
+                addressable.  They might be already used in the IL and thus
+                it is too late to make them addressable now though.  */
+             tree x = TREE_VALUE (link);
+             while (handled_component_p (x))
+               x = TREE_OPERAND (x, 0);
+             if (TREE_CODE (x) == MEM_REF
+                 && TREE_CODE (TREE_OPERAND (x, 0)) == ADDR_EXPR)
+               x = TREE_OPERAND (TREE_OPERAND (x, 0), 0);
+             if ((TREE_CODE (x) == VAR_DECL
+                  || TREE_CODE (x) == PARM_DECL
+                  || TREE_CODE (x) == RESULT_DECL)
+                 && !TREE_ADDRESSABLE (x)
+                 && is_gimple_reg (x))
+               {
+                 warning_at (EXPR_HAS_LOCATION (TREE_VALUE (link))
+                             ? EXPR_HAS_LOCATION (TREE_VALUE (link))
+                             : input_location, 0,
+                             "memory input %d is not directly addressable",
+                             i);
+                 prepare_gimple_addressable (&TREE_VALUE (link), pre_p);
+               }
+           }
          mark_addressable (TREE_VALUE (link));
          if (tret == GS_ERROR)
            {
-             if (EXPR_HAS_LOCATION (TREE_VALUE (link)))
-               input_location = EXPR_LOCATION (TREE_VALUE (link));
-             error ("memory input %d is not directly addressable", i);
+             error_at (EXPR_HAS_LOCATION (TREE_VALUE (link))
+                       ? EXPR_HAS_LOCATION (TREE_VALUE (link))
+                       : input_location,
+                       "memory input %d is not directly addressable", i);
              ret = tret;
            }
        }
--- gcc/testsuite/c-c++-common/pr67653.c.jj     2016-01-20 14:38:46.842942355 
+0100
+++ gcc/testsuite/c-c++-common/pr67653.c        2016-01-20 14:47:05.715989904 
+0100
@@ -0,0 +1,8 @@
+/* PR middle-end/67653 */
+/* { dg-do compile } */
+
+void
+foo (void)
+{
+  __asm__ ("" : : "m" (({ static int a; a; })));       /* { dg-warning "memory 
input 0 is not directly addressable" } */
+}
--- gcc/testsuite/gcc.dg/torture/pr29119.c.jj   2008-09-05 12:54:28.000000000 
+0200
+++ gcc/testsuite/gcc.dg/torture/pr29119.c      2016-01-20 14:47:14.867862361 
+0100
@@ -2,6 +2,5 @@
 
 void ldt_add_entry(void)
 {
-   __asm__ ("" :: "m"(({unsigned __v; __v;})));
+   __asm__ ("" :: "m"(({unsigned __v; __v;})));        /* { dg-warning "memory 
input 0 is not directly addressable" } */
 }
-


        Jakub

Reply via email to