On Thu, Oct 10, 2019 at 05:38:21PM -0400, Jason Merrill wrote:
> > FAIL: g++.dg/cpp2a/constexpr-dtor3.C  -std=c++2a (test for excess errors)
> > Excess errors:
> > /gcc/testsuite/g++.dg/cpp2a/constexpr-dtor3.C:152:12:   in 'constexpr'
> > expansion of '(& w13)->W7::~W7()'
> >
> 
> This also seems unrelated, but I'll take a look.
This is solely a location_t difference, comparing x86_64 and arm output
 constexpr-dtor3.C: At global scope:
 constexpr-dtor3.C:156:23:   in ‘constexpr’ expansion of ‘f4()’
-constexpr-dtor3.C:156:24:   in ‘constexpr’ expansion of ‘(& w13)->W7::~W7()’
+constexpr-dtor3.C:152:12:   in ‘constexpr’ expansion of ‘(& w13)->W7::~W7()’
 constexpr-dtor3.C:88:34: error: inline assembly is not a constant expression
    88 |   constexpr ~W7 () { if (w == 5) asm (""); w = 3; } // { dg-error 
"inline assembly is not a constant expression" }
       |                                  ^~~
 constexpr-dtor3.C:88:34: note: only unevaluated inline assembly is allowed in 
a ‘constexpr’ function in C++2a

constexpr int
f4 ()
{
  W7 w13 = 5;
  return 0;
}

constexpr int x4 = f4 ();       // { dg-message "in 'constexpr' expansion of" }

Line 152 is the W7 w13 = 5; line, line 156 the x4 = f4 () line.
>From warning POV, the arm locations are nicer, but see below.

The difference is in cxx_maybe_build_cleanup:

  /* build_delete sets the location of the destructor call to the
     current location, even though the destructor is going to be
     called later, at the end of the current scope.  This can lead to
     a "jumpy" behavior for users of debuggers when they step around
     the end of the block.  So let's unset the location of the
     destructor call instead.  */
  protected_set_expr_location (cleanup, UNKNOWN_LOCATION);

On x86_64 and most other targets, cleanup here (if non-NULL) is the
CALL_EXPR, as destructor return type is void, but on arm, as the dtor return
type is some pointer, the CALL_EXPR is wrapped into a NOP_EXPR to void.
protected_set_expr_location then on x86_64 clears the CALL_EXPR location,
but on arm only NOP_EXPR location.

The following patch (totally untested) should fix that.

For the warning location, perhaps we could special case destructor calls
in push_cx_call_context (to offset the intentional clearing of location for
debugging purposes), if they don't have location set, don't use
input_location for them, but try to pick DECL_SOURCE_LOCATION for the
variable being destructed?

2019-10-11  Jakub Jelinek  <ja...@redhat.com>

        * decl.c (cxx_maybe_build_cleanup): When clearing location of cleanup,
        if cleanup is a nop, clear location of its operand too.

--- gcc/cp/decl.c.jj    2019-10-10 01:33:38.154943945 +0200
+++ gcc/cp/decl.c       2019-10-11 10:09:24.321277942 +0200
@@ -16864,6 +16864,8 @@ cxx_maybe_build_cleanup (tree decl, tsub
      the end of the block.  So let's unset the location of the
      destructor call instead.  */
   protected_set_expr_location (cleanup, UNKNOWN_LOCATION);
+  if (cleanup && CONVERT_EXPR_P (cleanup))
+    protected_set_expr_location (TREE_OPERAND (cleanup, 0), UNKNOWN_LOCATION);
 
   if (cleanup
       && DECL_P (decl)


        Jakub

Reply via email to