]> git.ipfire.org Git - thirdparty/gcc.git/commitdiff
re PR c++/58063 (default arguments evaluated twice per call)
authorJason Merrill <jason@redhat.com>
Tue, 18 Aug 2015 14:43:38 +0000 (10:43 -0400)
committerJason Merrill <jason@gcc.gnu.org>
Tue, 18 Aug 2015 14:43:38 +0000 (10:43 -0400)
PR c++/58063
* tree.c (bot_manip): Remap SAVE_EXPR.

From-SVN: r226973

gcc/cp/ChangeLog
gcc/cp/tree.c
gcc/testsuite/g++.dg/overload/defarg10.C [new file with mode: 0644]

index 213e76dc1b2d27a4f784ece0661dd53ac1909b6b..4e239fa13c0188b8398febc9c284e11ad58196d8 100644 (file)
@@ -1,3 +1,8 @@
+2015-08-17  Jason Merrill  <jason@redhat.com>
+
+       PR c++/58063
+       * tree.c (bot_manip): Remap SAVE_EXPR.
+
 2015-07-16  Marek Polacek  <polacek@redhat.com>
 
        2015-07-08  Marek Polacek  <polacek@redhat.com>
index 0560781bae22470e074894d5596b00442720cf6a..348cec9a9ae41dd6d3a045b8b5d78dca572e47f0 100644 (file)
@@ -2314,6 +2314,29 @@ bot_manip (tree* tp, int* walk_subtrees, void* data)
       *walk_subtrees = 0;
       return NULL_TREE;
     }
+  if (TREE_CODE (*tp) == SAVE_EXPR)
+    {
+      t = *tp;
+      splay_tree_node n = splay_tree_lookup (target_remap,
+                                            (splay_tree_key) t);
+      if (n)
+       {
+         *tp = (tree)n->value;
+         *walk_subtrees = 0;
+       }
+      else
+       {
+         copy_tree_r (tp, walk_subtrees, NULL);
+         splay_tree_insert (target_remap,
+                            (splay_tree_key)t,
+                            (splay_tree_value)*tp);
+         /* Make sure we don't remap an already-remapped SAVE_EXPR.  */
+         splay_tree_insert (target_remap,
+                            (splay_tree_key)*tp,
+                            (splay_tree_value)*tp);
+       }
+      return NULL_TREE;
+    }
 
   /* Make a copy of this node.  */
   t = copy_tree_r (tp, walk_subtrees, NULL);
diff --git a/gcc/testsuite/g++.dg/overload/defarg10.C b/gcc/testsuite/g++.dg/overload/defarg10.C
new file mode 100644 (file)
index 0000000..b8275d6
--- /dev/null
@@ -0,0 +1,28 @@
+// PR c++/58063
+// { dg-do run }
+
+struct basic_ios
+{
+  bool operator!() const { return false; }
+};
+
+struct ostream : virtual basic_ios
+{
+};
+
+int i;
+
+ostream& operator<<(ostream& os, const char* s) {
+  ++i;
+  return os;
+}
+
+ostream cout;
+
+void f(bool x = !(cout << "hi!\n")) { }
+
+int main() {
+  f();
+  if (i != 1)
+    __builtin_abort();
+}