On 7/30/19 10:40 AM, Richard Biener wrote:
> On Tue, Jul 30, 2019 at 10:07 AM Martin Liška <mli...@suse.cz> wrote:
>>
>> On 7/30/19 9:46 AM, Martin Liška wrote:
>>> Anyway that's not a candidate for DCE. I'm testing following patch.
>>
>> Patch can bootstrap on x86_64-linux-gnu and survives regression tests.
>>
>> One alternative approach can be to drop DECL_SET_IS_OPERATOR_DELETE in:
>> cat -n gcc/cp/decl.c | less
>> ...
>>   4410          deltype = cp_build_type_attribute_variant (deltype, 
>> extvisattr);
>>   4411          deltype = build_exception_variant (deltype, 
>> empty_except_spec);
>>   4412          opdel = push_cp_library_fn (DELETE_EXPR, deltype, 
>> ECF_NOTHROW);
>>   4413          DECL_SET_IS_OPERATOR_DELETE (opdel, true);
>>   4414          opdel = push_cp_library_fn (VEC_DELETE_EXPR, deltype, 
>> ECF_NOTHROW);
>>   4415          DECL_SET_IS_OPERATOR_DELETE (opdel, true);
>>   4416
>>   4417          if (flag_sized_deallocation)
>>   4418            {
>>   4419              /* operator delete (void *, size_t, align_val_t); */
>>   4420              deltype = build_function_type_list (void_type_node, 
>> ptr_type_node,
>>   4421                                                  size_type_node, 
>> align_type_node,
>>   4422                                                  NULL_TREE);
>>   4423              deltype = cp_build_type_attribute_variant (deltype, 
>> extvisattr);
>>   4424              deltype = build_exception_variant (deltype, 
>> empty_except_spec);
>>   4425              opdel = push_cp_library_fn (DELETE_EXPR, deltype, 
>> ECF_NOTHROW);
>>   4426              DECL_SET_IS_OPERATOR_DELETE (opdel, true);
>>   4427              opdel = push_cp_library_fn (VEC_DELETE_EXPR, deltype, 
>> ECF_NOTHROW);
>>   4428              DECL_SET_IS_OPERATOR_DELETE (opdel, true);
>>   4429            }
>>   4430        }
>>
>> at lines 4426 and 4428.
>>
>> Richi what do you prefer?
> 
> I don't understand why a "not simple" delete operator isn't fine to be
> DCEd?  Does C++
> somehow allow mismatching size specifications here?

No, they are the same.

>  And what's the semantics
> then?
> 
> Thus I'd rather go with your earlier patch to mark the op necessary.

Ok, I'm sending tested patch.

Ready for trunk?
Thanks,
Martin

> 
> Richard.
> 
>> Martin

>From b4645189743b2670f77028933086fff56c46eb75 Mon Sep 17 00:00:00 2001
From: Martin Liska <mli...@suse.cz>
Date: Sun, 28 Jul 2019 13:04:28 +0200
Subject: [PATCH] Mark 2nd argument of delete operator as needed (PR
 tree-optimization/91270).

gcc/cp/ChangeLog:

2019-07-30  Martin Liska  <mli...@suse.cz>

	PR tree-optimization/91270
	* tree-ssa-dce.c (propagate_necessity): Mark 2nd argument
	of delete operator as needed.

gcc/testsuite/ChangeLog:

2019-07-30  Martin Liska  <mli...@suse.cz>

	PR tree-optimization/91270
	* g++.dg/torture/pr91270.C: New test.
---
 gcc/testsuite/g++.dg/torture/pr91270.C | 10 ++++++++++
 gcc/tree-ssa-dce.c                     | 19 +++++++++++++++----
 2 files changed, 25 insertions(+), 4 deletions(-)
 create mode 100644 gcc/testsuite/g++.dg/torture/pr91270.C

diff --git a/gcc/testsuite/g++.dg/torture/pr91270.C b/gcc/testsuite/g++.dg/torture/pr91270.C
new file mode 100644
index 00000000000..60d766e9e9f
--- /dev/null
+++ b/gcc/testsuite/g++.dg/torture/pr91270.C
@@ -0,0 +1,10 @@
+/* { dg-do compile } */
+
+struct S {
+  ~S();
+};
+int a = 123;
+void fn1() {
+  S *s = new S[a];
+  delete[] s;
+}
diff --git a/gcc/tree-ssa-dce.c b/gcc/tree-ssa-dce.c
index 763b76f0e53..c816fccceb4 100644
--- a/gcc/tree-ssa-dce.c
+++ b/gcc/tree-ssa-dce.c
@@ -804,10 +804,11 @@ propagate_necessity (bool aggressive)
 	  /* If this is a call to free which is directly fed by an
 	     allocation function do not mark that necessary through
 	     processing the argument.  */
+	  bool is_delete_operator
+	    = (is_gimple_call (stmt)
+	       && gimple_call_operator_delete_p (as_a <gcall *> (stmt)));
 	  if (gimple_call_builtin_p (stmt, BUILT_IN_FREE)
-	      || (is_gimple_call (stmt)
-		  && gimple_call_operator_delete_p (as_a <gcall *> (stmt))))
-
+	      || is_delete_operator)
 	    {
 	      tree ptr = gimple_call_arg (stmt, 0);
 	      gimple *def_stmt;
@@ -822,7 +823,17 @@ propagate_necessity (bool aggressive)
 			   || DECL_FUNCTION_CODE (def_callee) == BUILT_IN_MALLOC
 			   || DECL_FUNCTION_CODE (def_callee) == BUILT_IN_CALLOC))
 		      || DECL_IS_REPLACEABLE_OPERATOR_NEW_P (def_callee)))
-		continue;
+		{
+		  /* Some delete operators have size as 2nd argument.  */
+		  if (is_delete_operator && gimple_call_num_args (stmt) >= 2)
+		    {
+		      tree size_argument = gimple_call_arg (stmt, 1);
+		      if (TREE_CODE (size_argument) == SSA_NAME)
+			mark_operand_necessary (size_argument);
+		    }
+
+		  continue;
+		}
 	    }
 
 	  FOR_EACH_SSA_TREE_OPERAND (use, stmt, iter, SSA_OP_USE)
-- 
2.22.0

Reply via email to