[Bug middle-end/100861] False positive -Wmismatched-new-delete with destroying operator delete

2023-12-22 Thread pinskia at gcc dot gnu.org via Gcc-bugs
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=100861

Andrew Pinski  changed:

   What|Removed |Added

 CC||fchelnokov at gmail dot com

--- Comment #4 from Andrew Pinski  ---
*** Bug 113113 has been marked as a duplicate of this bug. ***

[Bug middle-end/100861] False positive -Wmismatched-new-delete with destroying operator delete

2021-06-01 Thread msebor at gcc dot gnu.org via Gcc-bugs
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=100861

--- Comment #3 from Martin Sebor  ---
The virtual dtor forces an out-of-line call to the Grommet dtor which then
calls ::operator delete(), so the warning has nothing to complain about.  It
sees this code (compile with -fdump-tree-optimized=/dev/stdout):

int main ()
{
  void * _3;

   [local count: 1073741824]:
  _3 = operator new (16);
  MEM[(struct Widget *)_3].Kind = 0;
  MEM[(struct Grommet *)_3].D.2504._vptr.Widget =   [(void
*)&_ZTV7Grommet + 16B];
  Grommet::~Grommet (_3);
  return 0;

}

whereas with the original test case it sees:

int main ()
{
  struct destroying_delete_t D.2584;
  void * _3;

   [local count: 1073741824]:
  _3 = operator new (4);
  Widget::operator delete (_3, D.2584);   <<< warning here
  return 0;

}

[Bug middle-end/100861] False positive -Wmismatched-new-delete with destroying operator delete

2021-06-01 Thread josephcsible at gmail dot com via Gcc-bugs
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=100861

--- Comment #2 from Joseph C. Sible  ---
Wait, if it's just checking whether the calls to operator new and operator
delete match up, then why does adding "virtual ~Widget() {}" make the warning
go away?

[Bug middle-end/100861] False positive -Wmismatched-new-delete with destroying operator delete

2021-06-01 Thread msebor at gcc dot gnu.org via Gcc-bugs
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=100861

Martin Sebor  changed:

   What|Removed |Added

   Severity|normal  |enhancement
 Status|UNCONFIRMED |NEW
  Component|c++ |middle-end
   Last reconfirmed||2021-06-01
 CC||msebor at gcc dot gnu.org
 Ever confirmed|0   |1
 Blocks||100406

--- Comment #1 from Martin Sebor  ---
The warning doesn't do anything special with destroying operator delete or any
other kinds of the operators (other than scalar vs array).  It triggers for
this test case because it sees the result of ::operator new() being passed to
Widget::operator delete (Widget*).  If Widget::operator delete() is inlined
(e.g., declared with attribute always_inline) the warning goes away just as
long as the operator doesn't pass the pointer to the wrong overload of delete. 
Alternatively, if Widget defines a non-inline member operator new() that also
prevents the warning because calls to both operators match.

With that, I'm not sure that suppressing the warning for a destroying operator
delete() would be a good solution.  It seems to me that the right fix is to
solve the broader problem where one of the operators is inlined and the other
isn't (similar to pr100485, except with the definitions of both operators
available in the same translation unit).

Until/unless a solution is developed I would suggest to either define the
destroying operator delete inline and have it call an out-of-line function to
do the work (as shown below) or to force the inlining of the destroying delete.

struct Widget {
  const WidgetKind Kind : 4;
  unsigned OtherThings : 28;

  Widget(WidgetKind k) : Kind(k) {}

  void operator delete(Widget *widget, std::destroying_delete_t) {
destroy_delete (widget);
  }

  static __attribute__ ((noinline)) void destroy_delete (Widget *);
};


Referenced Bugs:

https://gcc.gnu.org/bugzilla/show_bug.cgi?id=100406
[Bug 100406] bogus/missing -Wmismatched-new-delete