[Bug c++/120400] C++ FE optimisations reorder && operands.

2025-05-27 Thread cvs-commit at gcc dot gnu.org via Gcc-bugs
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=120400

--- Comment #17 from GCC Commits  ---
The trunk branch has been updated by Jason Merrill :

https://gcc.gnu.org/g:ee636671898c6bce63d9b2a698007b609aabbfe8

commit r16-919-gee636671898c6bce63d9b2a698007b609aabbfe8
Author: Jason Merrill 
Date:   Fri May 23 09:41:25 2025 -0400

fold: DECL_VALUE_EXPR isn't simple [PR120400]

This PR noted that fold_truth_andor was wrongly changing && to & where the
RHS is a VAR_DECL with DECL_VALUE_EXPR; we can't assume that such can be
evaluated unconditionally.

To be more precise we could recurse into DECL_VALUE_EXPR, but that doesn't
seem worth bothering with since typical uses involve a COMPONENT_REF, which
is not simple.

PR c++/120400

gcc/ChangeLog:

* fold-const.cc (simple_operand_p): False for vars with
DECL_VALUE_EXPR.

[Bug c++/120400] C++ FE optimisations reorder && operands.

2025-05-26 Thread iains at gcc dot gnu.org via Gcc-bugs
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=120400

--- Comment #16 from Iain Sandoe  ---
(In reply to Jason Merrill from comment #15)
> Created attachment 61520 [details]
> updated fix
> 
> Here's a better version of the patch, also sent to gcc-patches.

replied on-list, this also resolves the issue (with the typo fixes at comment
#14)

[Bug c++/120400] C++ FE optimisations reorder && operands.

2025-05-26 Thread jason at gcc dot gnu.org via Gcc-bugs
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=120400

Jason Merrill  changed:

   What|Removed |Added

  Attachment #61500|0   |1
is obsolete||

--- Comment #15 from Jason Merrill  ---
Created attachment 61520
  --> https://gcc.gnu.org/bugzilla/attachment.cgi?id=61520&action=edit
updated fix

Here's a better version of the patch, also sent to gcc-patches.

[Bug c++/120400] C++ FE optimisations reorder && operands.

2025-05-23 Thread iains at gcc dot gnu.org via Gcc-bugs
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=120400

Iain Sandoe  changed:

   What|Removed |Added

 Ever confirmed|0   |1
   Last reconfirmed||2025-05-23
 Status|UNCONFIRMED |NEW

--- Comment #14 from Iain Sandoe  ---
(In reply to Jason Merrill from comment #13)
> Created attachment 61500 [details]
> possible fix
> 
> Does this fix the issue?

Yes, it does .. that's the kind of thing I was hoping for ...

we also need the changes below - which I'll post separately.


@@ -5017,7 +5020,7 @@ cp_coroutine_transform::build_ramp_function ()
   tree frame_cleanup = push_stmt_list ();
   tree do_fr_cleanup
= build1_loc (loc, TRUTH_NOT_EXPR, boolean_type_node, iarc_x);
-  do_fr_cleanup = build2_loc (loc, TRUTH_AND_EXPR, boolean_type_node,
+  do_fr_cleanup = build2_loc (loc, TRUTH_ANDIF_EXPR, boolean_type_node,
  coro_before_return, do_fr_cleanup);
   r = build3 (COND_EXPR, void_type_node, do_fr_cleanup,
 delete_frame_call, void_node);
@@ -5109,7 +5112,7 @@ cp_coroutine_transform::build_ramp_function ()
  tree do_cleanup
= build1_loc (loc, TRUTH_NOT_EXPR, boolean_type_node,
iarc_x);
  do_cleanup
-   = build2_loc (loc, TRUTH_AND_EXPR, boolean_type_node,
+   = build2_loc (loc, TRUTH_ANDIF_EXPR, boolean_type_node,
  coro_before_return, do_cleanup);
  r = build3_loc (loc, COND_EXPR, void_type_node, do_cleanup,
  parm.fr_copy_dtor, void_node);
@@ -5169,7 +5172,7 @@ cp_coroutine_transform::build_ramp_function ()
  tree promise_cleanup = push_stmt_list ();
  tree do_cleanup
= build1_loc (loc, TRUTH_NOT_EXPR, boolean_type_node, iarc_x);
- do_cleanup = build2_loc (loc, TRUTH_AND_EXPR, boolean_type_node,
+ do_cleanup = build2_loc (loc, TRUTH_ANDIF_EXPR, boolean_type_node,
   coro_before_return, do_cleanup);
  r = build3 (COND_EXPR, void_type_node, do_cleanup,
  promise_dtor, void_node);

[Bug c++/120400] C++ FE optimisations reorder && operands.

2025-05-23 Thread jason at gcc dot gnu.org via Gcc-bugs
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=120400

--- Comment #13 from Jason Merrill  ---
Created attachment 61500
  --> https://gcc.gnu.org/bugzilla/attachment.cgi?id=61500&action=edit
possible fix

Does this fix the issue?

[Bug c++/120400] C++ FE optimisations reorder && operands.

2025-05-23 Thread iains at gcc dot gnu.org via Gcc-bugs
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=120400

--- Comment #12 from Iain Sandoe  ---
(In reply to Richard Biener from comment #11)
> D_V_E?  DECL_VALUE_EXPR? 

yes..

> I guess we should indeed treat those as having
> side-effects. 

struct F {
  bool b;
};

int foo (F *a)
{
  if (a && !a->b)
return 6;
  return 42;
}

Works as expected - but I do not see TREE_SIDE_EFFECTS set on any part of the
component ref expression.

I was going to investigate "looking through" expressions with a D_V_E and
applying the rules to the latter .. but not got to that yet.

> But without actually setting TREE_SIDE_EFFECTS that's hard to
> properly propagate everywhere, so yeah - I suggest doing that.

Hmm - seems a bit of a big hammer .. but.

[Bug c++/120400] C++ FE optimisations reorder && operands.

2025-05-23 Thread rguenth at gcc dot gnu.org via Gcc-bugs
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=120400

--- Comment #11 from Richard Biener  ---
D_V_E?  DECL_VALUE_EXPR?  I guess we should indeed treat those as having
side-effects.  But without actually setting TREE_SIDE_EFFECTS that's hard to
properly propagate everywhere, so yeah - I suggest doing that.

[Bug c++/120400] C++ FE optimisations reorder && operands.

2025-05-22 Thread iains at gcc dot gnu.org via Gcc-bugs
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=120400

--- Comment #10 from Iain Sandoe  ---
(In reply to Iain Sandoe from comment #8)
> (In reply to Andrew Pinski from comment #7)
> > I think if you set TREE_SIDE_EFFECTS on the decls that have a D_V_E, then it
> > might just work.
> 
> i can also try that (but I'd want to avoid doing something that's possibly
> fragile).

Setting that on the decls does "work" (as I read tree.h that is effectively
making those vars "volatile").  I'll do this for now, but would be interested
if there's some better strategy (other than doing two nested ifs).

[Bug c++/120400] C++ FE optimisations reorder && operands.

2025-05-22 Thread pinskia at gcc dot gnu.org via Gcc-bugs
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=120400

--- Comment #7 from Andrew Pinski  ---
I think if you set TREE_SIDE_EFFECTS on the decls that have a D_V_E, then it
might just work.

[Bug c++/120400] C++ FE optimisations reorder && operands.

2025-05-22 Thread pinskia at gcc dot gnu.org via Gcc-bugs
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=120400

--- Comment #9 from Andrew Pinski  ---
(In reply to Iain Sandoe from comment #8)
> (In reply to Andrew Pinski from comment #7)
> > I think if you set TREE_SIDE_EFFECTS on the decls that have a D_V_E, then it
> > might just work.
> 
> i can also try that (but I'd want to avoid doing something that's possibly
> fragile).
> 
> note that:
> 
> int foo (bool *a)
> {
>   if (a && !*a)
> return 6;
>   return 42;
> }
> 
> behaves as expected.

Right because INDIRECT_REF has TREE_SIDE_EFFECTS set on it when it is built.

[Bug c++/120400] C++ FE optimisations reorder && operands.

2025-05-22 Thread iains at gcc dot gnu.org via Gcc-bugs
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=120400

--- Comment #8 from Iain Sandoe  ---
(In reply to Andrew Pinski from comment #7)
> I think if you set TREE_SIDE_EFFECTS on the decls that have a D_V_E, then it
> might just work.

i can also try that (but I'd want to avoid doing something that's possibly
fragile).

note that:

int foo (bool *a)
{
  if (a && !*a)
return 6;
  return 42;
}

behaves as expected.

[Bug c++/120400] C++ FE optimisations reorder && operands.

2025-05-22 Thread pinskia at gcc dot gnu.org via Gcc-bugs
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=120400

--- Comment #6 from Andrew Pinski  ---
(In reply to Iain Sandoe from comment #5)
> 
> I must say it's also somewhat odd that the folder chooses the more expensive
> condition to come first - but then if there's no short-circuiting then all
> the ops will be done anyway.

That comes from tree_swap_operands_p:
  /* Put variables last.  */
  if (DECL_P (arg1))
return false;
  if (DECL_P (arg0))
return true;

[Bug c++/120400] C++ FE optimisations reorder && operands.

2025-05-22 Thread iains at gcc dot gnu.org via Gcc-bugs
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=120400

--- Comment #5 from Iain Sandoe  ---
(In reply to Iain Sandoe from comment #4)
> (In reply to Andrew Pinski from comment #3)
> > that is TRUTH_ANDIF_EXPR being converted into TRUTH_AND_EXPR in fold because
> > fold thinks coro_before_return and cond don't have side effects as they are
> > normal decls at the point fold is called.
> 
> hmm .. perhaps if a DECL has a D_V_E that should be blocked?
> (one of the decls is "normal" coro_before_return ,,, bu the other is not -
> it has a D_V_E pointing to the coroutine frame, and the folder probably
> should not be reasoning about that).
> 
> ?

I must say it's also somewhat odd that the folder chooses the more expensive
condition to come first - but then if there's no short-circuiting then all the
ops will be done anyway.

[Bug c++/120400] C++ FE optimisations reorder && operands.

2025-05-22 Thread iains at gcc dot gnu.org via Gcc-bugs
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=120400

--- Comment #4 from Iain Sandoe  ---
(In reply to Andrew Pinski from comment #3)
> that is TRUTH_ANDIF_EXPR being converted into TRUTH_AND_EXPR in fold because
> fold thinks coro_before_return and cond don't have side effects as they are
> normal decls at the point fold is called.

hmm .. perhaps if a DECL has a D_V_E that should be blocked?
(one of the decls is "normal" coro_before_return ,,, bu the other is not - it
has a D_V_E pointing to the coroutine frame, and the folder probably should not
be reasoning about that).

?

[Bug c++/120400] C++ FE optimisations reorder && operands.

2025-05-22 Thread pinskia at gcc dot gnu.org via Gcc-bugs
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=120400

Andrew Pinski  changed:

   What|Removed |Added

  Component|middle-end  |c++

--- Comment #3 from Andrew Pinski  ---
that is TRUTH_ANDIF_EXPR being converted into TRUTH_AND_EXPR in fold because
fold thinks coro_before_return and cond don't have side effects as they are
normal decls at the point fold is called.

[Bug c++/120400] C++ FE optimisations reorder && operands.

2025-05-22 Thread iains at gcc dot gnu.org via Gcc-bugs
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=120400

Iain Sandoe  changed:

   What|Removed |Added

Version|15.0|16.0

--- Comment #1 from Iain Sandoe  ---
trivial reproducer:


int foo (bool a, bool b)
{
  if (a && !b)
return 6;
  return 42;
}

I seee the same back to 10.5 (on x86_64-darwin21).